kucoin-api 2.1.23 → 2.2.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/README.md +111 -14
- package/dist/cjs/WebsocketAPIClient.d.ts +123 -0
- package/dist/cjs/WebsocketAPIClient.js +147 -0
- package/dist/cjs/WebsocketAPIClient.js.map +1 -0
- package/dist/cjs/WebsocketClient.d.ts +14 -9
- package/dist/cjs/WebsocketClient.js +277 -37
- package/dist/cjs/WebsocketClient.js.map +1 -1
- package/dist/cjs/index.d.ts +4 -3
- package/dist/cjs/index.js +4 -3
- package/dist/cjs/index.js.map +1 -1
- package/dist/cjs/lib/BaseRestClient.d.ts +16 -0
- package/dist/cjs/lib/BaseRestClient.js +46 -12
- package/dist/cjs/lib/BaseRestClient.js.map +1 -1
- package/dist/cjs/lib/BaseWSClient.d.ts +30 -17
- package/dist/cjs/lib/BaseWSClient.js +248 -55
- package/dist/cjs/lib/BaseWSClient.js.map +1 -1
- package/dist/cjs/lib/requestUtils.d.ts +11 -0
- package/dist/cjs/lib/requestUtils.js.map +1 -1
- package/dist/cjs/lib/websocket/WsStore.d.ts +15 -3
- package/dist/cjs/lib/websocket/WsStore.js +61 -12
- package/dist/cjs/lib/websocket/WsStore.js.map +1 -1
- package/dist/cjs/lib/websocket/WsStore.types.d.ts +6 -4
- package/dist/cjs/lib/websocket/WsStore.types.js +2 -2
- package/dist/cjs/lib/websocket/WsStore.types.js.map +1 -1
- package/dist/cjs/lib/websocket/logger.d.ts +1 -0
- package/dist/cjs/lib/websocket/websocket-util.d.ts +12 -6
- package/dist/cjs/lib/websocket/websocket-util.js +17 -8
- package/dist/cjs/lib/websocket/websocket-util.js.map +1 -1
- package/dist/cjs/types/request/futures.types.d.ts +1 -0
- package/dist/cjs/types/websockets/ws-api.d.ts +123 -0
- package/dist/cjs/types/websockets/ws-api.js +22 -0
- package/dist/cjs/types/websockets/ws-api.js.map +1 -0
- package/dist/cjs/types/websockets/ws-events.d.ts +11 -0
- package/dist/cjs/types/websockets/ws-events.js +11 -0
- package/dist/cjs/types/websockets/ws-events.js.map +1 -0
- package/dist/cjs/types/websockets/{client.d.ts → ws-general.d.ts} +5 -0
- package/dist/cjs/types/websockets/{events.js → ws-general.js} +1 -1
- package/dist/cjs/types/websockets/ws-general.js.map +1 -0
- package/dist/mjs/WebsocketAPIClient.d.ts +123 -0
- package/dist/mjs/WebsocketAPIClient.js +143 -0
- package/dist/mjs/WebsocketAPIClient.js.map +1 -0
- package/dist/mjs/WebsocketClient.d.ts +14 -9
- package/dist/mjs/WebsocketClient.js +278 -38
- package/dist/mjs/WebsocketClient.js.map +1 -1
- package/dist/mjs/index.d.ts +4 -3
- package/dist/mjs/index.js +4 -3
- package/dist/mjs/index.js.map +1 -1
- package/dist/mjs/lib/BaseRestClient.d.ts +16 -0
- package/dist/mjs/lib/BaseRestClient.js +47 -13
- package/dist/mjs/lib/BaseRestClient.js.map +1 -1
- package/dist/mjs/lib/BaseWSClient.d.ts +30 -17
- package/dist/mjs/lib/BaseWSClient.js +248 -55
- package/dist/mjs/lib/BaseWSClient.js.map +1 -1
- package/dist/mjs/lib/requestUtils.d.ts +11 -0
- package/dist/mjs/lib/requestUtils.js.map +1 -1
- package/dist/mjs/lib/websocket/WsStore.d.ts +15 -3
- package/dist/mjs/lib/websocket/WsStore.js +61 -12
- package/dist/mjs/lib/websocket/WsStore.js.map +1 -1
- package/dist/mjs/lib/websocket/WsStore.types.d.ts +6 -4
- package/dist/mjs/lib/websocket/WsStore.types.js +2 -2
- package/dist/mjs/lib/websocket/WsStore.types.js.map +1 -1
- package/dist/mjs/lib/websocket/logger.d.ts +1 -0
- package/dist/mjs/lib/websocket/websocket-util.d.ts +12 -6
- package/dist/mjs/lib/websocket/websocket-util.js +15 -7
- package/dist/mjs/lib/websocket/websocket-util.js.map +1 -1
- package/dist/mjs/types/request/futures.types.d.ts +1 -0
- package/dist/mjs/types/websockets/ws-api.d.ts +123 -0
- package/dist/mjs/types/websockets/ws-api.js +19 -0
- package/dist/mjs/types/websockets/ws-api.js.map +1 -0
- package/dist/mjs/types/websockets/ws-events.d.ts +11 -0
- package/dist/mjs/types/websockets/ws-events.js +8 -0
- package/dist/mjs/types/websockets/ws-events.js.map +1 -0
- package/dist/mjs/types/websockets/{client.d.ts → ws-general.d.ts} +5 -0
- package/dist/mjs/types/websockets/ws-general.js +2 -0
- package/dist/mjs/types/websockets/ws-general.js.map +1 -0
- package/llms.txt +5985 -4979
- package/package.json +6 -4
- package/dist/cjs/types/websockets/client.js +0 -3
- package/dist/cjs/types/websockets/client.js.map +0 -1
- package/dist/cjs/types/websockets/events.d.ts +0 -5
- package/dist/cjs/types/websockets/events.js.map +0 -1
- package/dist/cjs/types/websockets/requests.d.ts +0 -8
- package/dist/cjs/types/websockets/requests.js +0 -3
- package/dist/cjs/types/websockets/requests.js.map +0 -1
- package/dist/cjs/types/websockets/wsAPI.d.ts +0 -9
- package/dist/cjs/types/websockets/wsAPI.js +0 -3
- package/dist/cjs/types/websockets/wsAPI.js.map +0 -1
- package/dist/mjs/types/websockets/client.js +0 -2
- package/dist/mjs/types/websockets/client.js.map +0 -1
- package/dist/mjs/types/websockets/events.d.ts +0 -5
- package/dist/mjs/types/websockets/events.js +0 -2
- package/dist/mjs/types/websockets/events.js.map +0 -1
- package/dist/mjs/types/websockets/requests.d.ts +0 -8
- package/dist/mjs/types/websockets/requests.js +0 -2
- package/dist/mjs/types/websockets/requests.js.map +0 -1
- package/dist/mjs/types/websockets/wsAPI.d.ts +0 -9
- package/dist/mjs/types/websockets/wsAPI.js +0 -2
- package/dist/mjs/types/websockets/wsAPI.js.map +0 -1
|
@@ -17,6 +17,11 @@ export interface RestClientOptions {
|
|
|
17
17
|
apiSecret?: string;
|
|
18
18
|
/** Your API passphrase (can be anything) that you set when creating this API key (NOT your account password) */
|
|
19
19
|
apiPassphrase?: string;
|
|
20
|
+
/**
|
|
21
|
+
* Use access token instead of sign, if this is provided.
|
|
22
|
+
* For guidance refer to: https://github.com/tiagosiebler/kucoin-api/issues/2
|
|
23
|
+
*/
|
|
24
|
+
apiAccessToken?: string;
|
|
20
25
|
/** The API key version. Defaults to "2" right now. You can see this in your API management page */
|
|
21
26
|
apiKeyVersion?: number | string;
|
|
22
27
|
/** Default: false. If true, we'll throw errors if any params are undefined */
|
|
@@ -39,6 +44,12 @@ export interface RestClientOptions {
|
|
|
39
44
|
* Default: 1000 (defaults comes from https agent)
|
|
40
45
|
*/
|
|
41
46
|
keepAliveMsecs?: number;
|
|
47
|
+
/**
|
|
48
|
+
* Allows you to provide a custom "signMessage" function, e.g. to use node's much faster createHmac method
|
|
49
|
+
*
|
|
50
|
+
* Look in the examples folder for a demonstration on using node's createHmac instead.
|
|
51
|
+
*/
|
|
52
|
+
customSignMessageFn?: (message: string, secret: string) => Promise<string>;
|
|
42
53
|
}
|
|
43
54
|
export declare function serializeParams<T extends Record<string, any> | undefined = {}>(params: T, strict_validation: boolean | undefined, encodeValues: boolean, prefixWith: string): string;
|
|
44
55
|
export declare const APIIDMain = "NODESDK";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"requestUtils.js","sourceRoot":"","sources":["../../../src/lib/requestUtils.ts"],"names":[],"mappings":";;;
|
|
1
|
+
{"version":3,"file":"requestUtils.js","sourceRoot":"","sources":["../../../src/lib/requestUtils.ts"],"names":[],"mappings":";;;AA0EA,0CA0BC;AAQD,wCAmBC;AA/HD;;GAEG;AACU,QAAA,qBAAqB,GAAG;IACnC,oBAAoB;IACpB,IAAI,EAAE,MAAM;IACZ,cAAc;IACd,OAAO,EAAE,SAAS;IAClB,aAAa;IACb,MAAM,EAAE,QAAQ;CACR,CAAC;AAKX,MAAM,YAAY,GAAG;IACnB,CAAC,6BAAqB,CAAC,IAAI,CAAC,EAAE,wBAAwB;IACtD,CAAC,6BAAqB,CAAC,OAAO,CAAC,EAAE,gCAAgC;IACjE,CAAC,6BAAqB,CAAC,MAAM,CAAC,EAAE,+BAA+B;CACvD,CAAC;AAuDX,SAAgB,eAAe,CAC7B,MAAS,EACT,iBAAsC,EACtC,YAAqB,EACrB,UAAkB;IAElB,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,OAAO,EAAE,CAAC;IACZ,CAAC;IAED,MAAM,WAAW,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC;SACpC,IAAI,EAAE;SACN,GAAG,CAAC,CAAC,GAAG,EAAE,EAAE;QACX,MAAM,KAAK,GAAG,MAAM,CAAC,GAAG,CAAC,CAAC;QAC1B,IAAI,iBAAiB,KAAK,IAAI,IAAI,OAAO,KAAK,KAAK,WAAW,EAAE,CAAC;YAC/D,MAAM,IAAI,KAAK,CACb,uDAAuD,CACxD,CAAC;QACJ,CAAC;QACD,MAAM,YAAY,GAAG,YAAY,CAAC,CAAC,CAAC,kBAAkB,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;QACtE,OAAO,GAAG,GAAG,IAAI,YAAY,EAAE,CAAC;IAClC,CAAC,CAAC;SACD,IAAI,CAAC,GAAG,CAAC,CAAC;IAEb,iCAAiC;IACjC,OAAO,WAAW,CAAC,CAAC,CAAC,UAAU,GAAG,WAAW,CAAC,CAAC,CAAC,WAAW,CAAC;AAC9D,CAAC;AAEY,QAAA,SAAS,GAAG,SAAS,CAAC;AACtB,QAAA,aAAa,GAAG,sCAAsC,CAAC;AAEvD,QAAA,YAAY,GAAG,gBAAgB,CAAC;AAChC,QAAA,gBAAgB,GAAG,sCAAsC,CAAC;AAEvE,SAAgB,cAAc,CAC5B,UAAmB,EACnB,kBAAqC,EACrC,cAA8B;IAE9B,MAAM,gBAAgB,GAAG;QACvB,OAAO,EAAE,YAAY,CAAC,cAAc,CAAC;QACrC,OAAO,EAAE,mBAAmB;KAC7B,CAAC;IAEF,IAAI,kBAAkB,CAAC,OAAO,EAAE,CAAC;QAC/B,OAAO,kBAAkB,CAAC,OAAO,CAAC;IACpC,CAAC;IAED,IAAI,UAAU,EAAE,CAAC;QACf,OAAO,gBAAgB,CAAC,OAAO,CAAC;IAClC,CAAC;IAED,OAAO,gBAAgB,CAAC,OAAO,CAAC;AAClC,CAAC"}
|
|
@@ -2,17 +2,18 @@ import WebSocket from 'isomorphic-ws';
|
|
|
2
2
|
import { DefaultLogger } from './logger.js';
|
|
3
3
|
import { DeferredPromise, WSConnectedResult, WsConnectionStateEnum, WsStoredState } from './WsStore.types.js';
|
|
4
4
|
/**
|
|
5
|
-
* Simple comparison of two objects,
|
|
5
|
+
* Simple comparison of two objects, recursive for nested objects. Adoped from OKX SDK.
|
|
6
6
|
*/
|
|
7
|
-
export declare function isDeepObjectMatch(object1:
|
|
7
|
+
export declare function isDeepObjectMatch(object1: any, object2: any): boolean;
|
|
8
8
|
declare const DEFERRED_PROMISE_REF: {
|
|
9
9
|
readonly CONNECTION_IN_PROGRESS: "CONNECTION_IN_PROGRESS";
|
|
10
|
+
readonly AUTHENTICATION_IN_PROGRESS: "AUTHENTICATION_IN_PROGRESS";
|
|
10
11
|
};
|
|
11
12
|
type DeferredPromiseRef = (typeof DEFERRED_PROMISE_REF)[keyof typeof DEFERRED_PROMISE_REF];
|
|
12
13
|
export declare class WsStore<WsKey extends string, TWSTopicSubscribeEventArgs extends string | object> {
|
|
13
14
|
private wsState;
|
|
14
15
|
private logger;
|
|
15
|
-
constructor(logger:
|
|
16
|
+
constructor(logger: DefaultLogger);
|
|
16
17
|
/** Get WS stored state for key, optionally create if missing */
|
|
17
18
|
get(key: WsKey, createIfMissing?: true): WsStoredState<TWSTopicSubscribeEventArgs>;
|
|
18
19
|
get(key: WsKey, createIfMissing?: false): WsStoredState<TWSTopicSubscribeEventArgs> | undefined;
|
|
@@ -22,6 +23,9 @@ export declare class WsStore<WsKey extends string, TWSTopicSubscribeEventArgs ex
|
|
|
22
23
|
hasExistingActiveConnection(key: WsKey): boolean;
|
|
23
24
|
getWs(key: WsKey): WebSocket | undefined;
|
|
24
25
|
setWs(key: WsKey, wsConnection: WebSocket): WebSocket;
|
|
26
|
+
/**
|
|
27
|
+
* deferred promises
|
|
28
|
+
*/
|
|
25
29
|
getDeferredPromise<TSuccessResult = any>(wsKey: WsKey, promiseRef: string | DeferredPromiseRef): DeferredPromise<TSuccessResult> | undefined;
|
|
26
30
|
createDeferredPromise<TSuccessResult = any>(wsKey: WsKey, promiseRef: string | DeferredPromiseRef, throwIfExists: boolean): DeferredPromise<TSuccessResult>;
|
|
27
31
|
resolveDeferredPromise(wsKey: WsKey, promiseRef: string | DeferredPromiseRef, value: unknown, removeAfter: boolean): void;
|
|
@@ -30,14 +34,21 @@ export declare class WsStore<WsKey extends string, TWSTopicSubscribeEventArgs ex
|
|
|
30
34
|
rejectAllDeferredPromises(wsKey: WsKey, reason: string): void;
|
|
31
35
|
/** Get promise designed to track a connection attempt in progress. Resolves once connected. */
|
|
32
36
|
getConnectionInProgressPromise(wsKey: WsKey): DeferredPromise<WSConnectedResult> | undefined;
|
|
37
|
+
getAuthenticationInProgressPromise(wsKey: WsKey): DeferredPromise<WSConnectedResult & {
|
|
38
|
+
event: any;
|
|
39
|
+
}> | undefined;
|
|
33
40
|
/**
|
|
34
41
|
* Create a deferred promise designed to track a connection attempt in progress.
|
|
35
42
|
*
|
|
36
43
|
* Will throw if existing promise is found.
|
|
37
44
|
*/
|
|
38
45
|
createConnectionInProgressPromise(wsKey: WsKey, throwIfExists: boolean): DeferredPromise<WSConnectedResult>;
|
|
46
|
+
createAuthenticationInProgressPromise(wsKey: WsKey, throwIfExists: boolean): DeferredPromise<WSConnectedResult & {
|
|
47
|
+
event: any;
|
|
48
|
+
}>;
|
|
39
49
|
/** Remove promise designed to track a connection attempt in progress */
|
|
40
50
|
removeConnectingInProgressPromise(wsKey: WsKey): void;
|
|
51
|
+
removeAuthenticationInProgressPromise(wsKey: WsKey): void;
|
|
41
52
|
isWsOpen(key: WsKey): boolean;
|
|
42
53
|
getConnectionState(key: WsKey): WsConnectionStateEnum;
|
|
43
54
|
setConnectionState(key: WsKey, state: WsConnectionStateEnum): void;
|
|
@@ -49,6 +60,7 @@ export declare class WsStore<WsKey extends string, TWSTopicSubscribeEventArgs ex
|
|
|
49
60
|
*/
|
|
50
61
|
isConnectionAttemptInProgress(key: WsKey): boolean;
|
|
51
62
|
getTopics(key: WsKey): Set<TWSTopicSubscribeEventArgs>;
|
|
63
|
+
getTopicsAsArray(key: WsKey): TWSTopicSubscribeEventArgs[];
|
|
52
64
|
getTopicsByKey(): Record<string, Set<TWSTopicSubscribeEventArgs>>;
|
|
53
65
|
/**
|
|
54
66
|
* Find matching "topic" request from the store
|
|
@@ -5,18 +5,33 @@ exports.isDeepObjectMatch = isDeepObjectMatch;
|
|
|
5
5
|
const logger_js_1 = require("./logger.js");
|
|
6
6
|
const WsStore_types_js_1 = require("./WsStore.types.js");
|
|
7
7
|
/**
|
|
8
|
-
* Simple comparison of two objects,
|
|
8
|
+
* Simple comparison of two objects, recursive for nested objects. Adoped from OKX SDK.
|
|
9
9
|
*/
|
|
10
10
|
function isDeepObjectMatch(object1, object2) {
|
|
11
|
-
if (typeof
|
|
12
|
-
return
|
|
11
|
+
if (typeof object2 !== typeof object1) {
|
|
12
|
+
return false;
|
|
13
|
+
}
|
|
14
|
+
const keys1 = Object.keys(object1).sort();
|
|
15
|
+
const keys2 = Object.keys(object2).sort();
|
|
16
|
+
const hasSameKeyCount = keys1.length === keys2.length;
|
|
17
|
+
if (!hasSameKeyCount) {
|
|
18
|
+
// console.log('not same key count', { keys1, keys2 });
|
|
19
|
+
// not the same amount of keys or keys don't match
|
|
20
|
+
return false;
|
|
13
21
|
}
|
|
14
|
-
|
|
22
|
+
const hasSameKeyNames = keys1.every((val, i) => val === keys2[i]);
|
|
23
|
+
if (!hasSameKeyNames) {
|
|
24
|
+
// console.log('not same key names: ', { keys1, keys2 });
|
|
15
25
|
return false;
|
|
16
26
|
}
|
|
17
27
|
for (const key in object1) {
|
|
18
28
|
const value1 = object1[key];
|
|
19
29
|
const value2 = object2[key];
|
|
30
|
+
if (typeof value1 === 'object' && typeof value2 === 'object') {
|
|
31
|
+
if (!isDeepObjectMatch(value1, value2)) {
|
|
32
|
+
return false;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
20
35
|
if (value1 !== value2) {
|
|
21
36
|
return false;
|
|
22
37
|
}
|
|
@@ -25,6 +40,7 @@ function isDeepObjectMatch(object1, object2) {
|
|
|
25
40
|
}
|
|
26
41
|
const DEFERRED_PROMISE_REF = {
|
|
27
42
|
CONNECTION_IN_PROGRESS: 'CONNECTION_IN_PROGRESS',
|
|
43
|
+
AUTHENTICATION_IN_PROGRESS: 'AUTHENTICATION_IN_PROGRESS',
|
|
28
44
|
};
|
|
29
45
|
class WsStore {
|
|
30
46
|
wsState = {};
|
|
@@ -77,6 +93,9 @@ class WsStore {
|
|
|
77
93
|
this.get(key, true).ws = wsConnection;
|
|
78
94
|
return wsConnection;
|
|
79
95
|
}
|
|
96
|
+
/**
|
|
97
|
+
* deferred promises
|
|
98
|
+
*/
|
|
80
99
|
getDeferredPromise(wsKey, promiseRef) {
|
|
81
100
|
const storeForKey = this.get(wsKey);
|
|
82
101
|
if (!storeForKey) {
|
|
@@ -121,7 +140,13 @@ class WsStore {
|
|
|
121
140
|
rejectDeferredPromise(wsKey, promiseRef, value, removeAfter) {
|
|
122
141
|
const promise = this.getDeferredPromise(wsKey, promiseRef);
|
|
123
142
|
if (promise?.reject) {
|
|
124
|
-
|
|
143
|
+
this.logger.trace(`rejectDeferredPromise(): rejecting ${wsKey}/${promiseRef}`, value);
|
|
144
|
+
if (typeof value === 'string') {
|
|
145
|
+
promise.reject(new Error(value));
|
|
146
|
+
}
|
|
147
|
+
else {
|
|
148
|
+
promise.reject(value);
|
|
149
|
+
}
|
|
125
150
|
}
|
|
126
151
|
if (removeAfter) {
|
|
127
152
|
this.removeDeferredPromise(wsKey, promiseRef);
|
|
@@ -154,6 +179,7 @@ class WsStore {
|
|
|
154
179
|
continue;
|
|
155
180
|
}
|
|
156
181
|
try {
|
|
182
|
+
this.logger.trace(`rejectAllDeferredPromises(): rejecting ${wsKey}/${promiseRef}/${reason}`);
|
|
157
183
|
this.rejectDeferredPromise(wsKey, promiseRef, reason, true);
|
|
158
184
|
}
|
|
159
185
|
catch (e) {
|
|
@@ -165,6 +191,9 @@ class WsStore {
|
|
|
165
191
|
getConnectionInProgressPromise(wsKey) {
|
|
166
192
|
return this.getDeferredPromise(wsKey, DEFERRED_PROMISE_REF.CONNECTION_IN_PROGRESS);
|
|
167
193
|
}
|
|
194
|
+
getAuthenticationInProgressPromise(wsKey) {
|
|
195
|
+
return this.getDeferredPromise(wsKey, DEFERRED_PROMISE_REF.AUTHENTICATION_IN_PROGRESS);
|
|
196
|
+
}
|
|
168
197
|
/**
|
|
169
198
|
* Create a deferred promise designed to track a connection attempt in progress.
|
|
170
199
|
*
|
|
@@ -173,10 +202,16 @@ class WsStore {
|
|
|
173
202
|
createConnectionInProgressPromise(wsKey, throwIfExists) {
|
|
174
203
|
return this.createDeferredPromise(wsKey, DEFERRED_PROMISE_REF.CONNECTION_IN_PROGRESS, throwIfExists);
|
|
175
204
|
}
|
|
205
|
+
createAuthenticationInProgressPromise(wsKey, throwIfExists) {
|
|
206
|
+
return this.createDeferredPromise(wsKey, DEFERRED_PROMISE_REF.AUTHENTICATION_IN_PROGRESS, throwIfExists);
|
|
207
|
+
}
|
|
176
208
|
/** Remove promise designed to track a connection attempt in progress */
|
|
177
209
|
removeConnectingInProgressPromise(wsKey) {
|
|
178
210
|
return this.removeDeferredPromise(wsKey, DEFERRED_PROMISE_REF.CONNECTION_IN_PROGRESS);
|
|
179
211
|
}
|
|
212
|
+
removeAuthenticationInProgressPromise(wsKey) {
|
|
213
|
+
return this.removeDeferredPromise(wsKey, DEFERRED_PROMISE_REF.AUTHENTICATION_IN_PROGRESS);
|
|
214
|
+
}
|
|
180
215
|
/* connection state */
|
|
181
216
|
isWsOpen(key) {
|
|
182
217
|
const existingConnection = this.getWs(key);
|
|
@@ -187,8 +222,8 @@ class WsStore {
|
|
|
187
222
|
return this.get(key, true).connectionState;
|
|
188
223
|
}
|
|
189
224
|
setConnectionState(key, state) {
|
|
190
|
-
// console.log(new Date(), `setConnectionState(${key}, ${state})`);
|
|
191
225
|
this.get(key, true).connectionState = state;
|
|
226
|
+
this.get(key, true).connectionStateChangedAt = new Date();
|
|
192
227
|
}
|
|
193
228
|
isConnectionState(key, state) {
|
|
194
229
|
return this.getConnectionState(key) === state;
|
|
@@ -201,12 +236,30 @@ class WsStore {
|
|
|
201
236
|
isConnectionAttemptInProgress(key) {
|
|
202
237
|
const isConnectionInProgress = this.isConnectionState(key, WsStore_types_js_1.WsConnectionStateEnum.CONNECTING) ||
|
|
203
238
|
this.isConnectionState(key, WsStore_types_js_1.WsConnectionStateEnum.RECONNECTING);
|
|
239
|
+
if (isConnectionInProgress) {
|
|
240
|
+
const wsState = this.get(key, true);
|
|
241
|
+
const stateLastChangedAt = wsState?.connectionStateChangedAt;
|
|
242
|
+
const stateChangedAtTimestamp = stateLastChangedAt?.getTime();
|
|
243
|
+
if (stateChangedAtTimestamp) {
|
|
244
|
+
const timestampNow = new Date().getTime();
|
|
245
|
+
const stateChangedTimeAgo = timestampNow - stateChangedAtTimestamp;
|
|
246
|
+
const stateChangeTimeout = 15000; // allow a max 15 second timeout since the last state change before assuming stuck;
|
|
247
|
+
if (stateChangedTimeAgo >= stateChangeTimeout) {
|
|
248
|
+
const msg = 'State change timed out, reconnect workflow stuck?';
|
|
249
|
+
this.logger.error(msg, { key, wsState });
|
|
250
|
+
this.setConnectionState(key, WsStore_types_js_1.WsConnectionStateEnum.ERROR);
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
}
|
|
204
254
|
return isConnectionInProgress;
|
|
205
255
|
}
|
|
206
256
|
/* subscribed topics */
|
|
207
257
|
getTopics(key) {
|
|
208
258
|
return this.get(key, true).subscribedTopics;
|
|
209
259
|
}
|
|
260
|
+
getTopicsAsArray(key) {
|
|
261
|
+
return [...this.getTopics(key).values()];
|
|
262
|
+
}
|
|
210
263
|
getTopicsByKey() {
|
|
211
264
|
const result = {};
|
|
212
265
|
for (const refKey in this.wsState) {
|
|
@@ -214,7 +267,6 @@ class WsStore {
|
|
|
214
267
|
}
|
|
215
268
|
return result;
|
|
216
269
|
}
|
|
217
|
-
// Since topics are objects we can't rely on the set to detect duplicates
|
|
218
270
|
/**
|
|
219
271
|
* Find matching "topic" request from the store
|
|
220
272
|
* @param key
|
|
@@ -222,18 +274,15 @@ class WsStore {
|
|
|
222
274
|
* @returns
|
|
223
275
|
*/
|
|
224
276
|
getMatchingTopic(key, topic) {
|
|
225
|
-
// if (typeof topic === 'string') {
|
|
226
|
-
// return this.getMatchingTopic(key, { channel: topic });
|
|
227
|
-
// }
|
|
228
277
|
const allTopics = this.getTopics(key).values();
|
|
229
278
|
for (const storedTopic of allTopics) {
|
|
230
|
-
|
|
279
|
+
const matchesStoredTopic = isDeepObjectMatch(topic, storedTopic);
|
|
280
|
+
if (matchesStoredTopic) {
|
|
231
281
|
return storedTopic;
|
|
232
282
|
}
|
|
233
283
|
}
|
|
234
284
|
}
|
|
235
285
|
addTopic(key, topic) {
|
|
236
|
-
// console.log(`wsStore.addTopic(${key}, ${topic})`);
|
|
237
286
|
// Check for duplicate topic. If already tracked, don't store this one
|
|
238
287
|
const existingTopic = this.getMatchingTopic(key, topic);
|
|
239
288
|
if (existingTopic) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WsStore.js","sourceRoot":"","sources":["../../../../src/lib/websocket/WsStore.ts"],"names":[],"mappings":";;;AAaA,
|
|
1
|
+
{"version":3,"file":"WsStore.js","sourceRoot":"","sources":["../../../../src/lib/websocket/WsStore.ts"],"names":[],"mappings":"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"}
|
|
@@ -5,7 +5,7 @@ export declare enum WsConnectionStateEnum {
|
|
|
5
5
|
CONNECTED = 2,
|
|
6
6
|
CLOSING = 3,
|
|
7
7
|
RECONNECTING = 4,
|
|
8
|
-
|
|
8
|
+
ERROR = 5
|
|
9
9
|
}
|
|
10
10
|
export interface DeferredPromise<TSuccess = any, TError = any> {
|
|
11
11
|
resolve?: (value: TSuccess) => TSuccess;
|
|
@@ -14,12 +14,14 @@ export interface DeferredPromise<TSuccess = any, TError = any> {
|
|
|
14
14
|
}
|
|
15
15
|
export interface WSConnectedResult {
|
|
16
16
|
wsKey: string;
|
|
17
|
+
ws: WebSocket;
|
|
17
18
|
}
|
|
18
19
|
export interface WsStoredState<TWSTopicSubscribeEvent extends string | object> {
|
|
19
20
|
/** The currently active websocket connection */
|
|
20
21
|
ws?: WebSocket;
|
|
21
22
|
/** The current lifecycle state of the connection (enum) */
|
|
22
23
|
connectionState?: WsConnectionStateEnum;
|
|
24
|
+
connectionStateChangedAt?: Date;
|
|
23
25
|
/** A timer that will send an upstream heartbeat (ping) when it expires */
|
|
24
26
|
activePingTimer?: ReturnType<typeof setTimeout> | undefined;
|
|
25
27
|
/** A timer tracking that an upstream heartbeat was sent, expecting a reply before it expires */
|
|
@@ -38,11 +40,11 @@ export interface WsStoredState<TWSTopicSubscribeEvent extends string | object> {
|
|
|
38
40
|
* A "Set" and a deep-object-match are used to ensure we only subscribe to a topic once (tracking a list of unique topics we're expected to be connected to)
|
|
39
41
|
*/
|
|
40
42
|
subscribedTopics: Set<TWSTopicSubscribeEvent>;
|
|
41
|
-
/** Whether this connection is ready for events (welcome message received after connection) */
|
|
42
|
-
isReadyForEvents?: boolean;
|
|
43
43
|
/** Whether this connection has completed authentication (only applies to private connections) */
|
|
44
44
|
isAuthenticated?: boolean;
|
|
45
|
-
/**
|
|
45
|
+
/**
|
|
46
|
+
* Whether this connection has completed authentication before for the Websocket API, so it knows to automatically reauth if reconnected
|
|
47
|
+
*/
|
|
46
48
|
didAuthWSAPI?: boolean;
|
|
47
49
|
/** To reauthenticate on the WS API, which channel do we send to? */
|
|
48
50
|
WSAPIAuthChannel?: string;
|
|
@@ -8,7 +8,7 @@ var WsConnectionStateEnum;
|
|
|
8
8
|
WsConnectionStateEnum[WsConnectionStateEnum["CONNECTED"] = 2] = "CONNECTED";
|
|
9
9
|
WsConnectionStateEnum[WsConnectionStateEnum["CLOSING"] = 3] = "CLOSING";
|
|
10
10
|
WsConnectionStateEnum[WsConnectionStateEnum["RECONNECTING"] = 4] = "RECONNECTING";
|
|
11
|
-
|
|
12
|
-
|
|
11
|
+
// ERROR_RECONNECTING = 5,
|
|
12
|
+
WsConnectionStateEnum[WsConnectionStateEnum["ERROR"] = 5] = "ERROR";
|
|
13
13
|
})(WsConnectionStateEnum || (exports.WsConnectionStateEnum = WsConnectionStateEnum = {}));
|
|
14
14
|
//# sourceMappingURL=WsStore.types.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"WsStore.types.js","sourceRoot":"","sources":["../../../../src/lib/websocket/WsStore.types.ts"],"names":[],"mappings":";;;AAEA,IAAY,qBAQX;AARD,WAAY,qBAAqB;IAC/B,uEAAW,CAAA;IACX,6EAAc,CAAA;IACd,2EAAa,CAAA;IACb,uEAAW,CAAA;IACX,iFAAgB,CAAA;IAChB,
|
|
1
|
+
{"version":3,"file":"WsStore.types.js","sourceRoot":"","sources":["../../../../src/lib/websocket/WsStore.types.ts"],"names":[],"mappings":";;;AAEA,IAAY,qBAQX;AARD,WAAY,qBAAqB;IAC/B,uEAAW,CAAA;IACX,6EAAc,CAAA;IACd,2EAAa,CAAA;IACb,uEAAW,CAAA;IACX,iFAAgB,CAAA;IAChB,0BAA0B;IAC1B,mEAAS,CAAA;AACX,CAAC,EARW,qBAAqB,qCAArB,qBAAqB,QAQhC"}
|
|
@@ -1,13 +1,17 @@
|
|
|
1
1
|
import WebSocket from 'isomorphic-ws';
|
|
2
|
+
import { WsRequestOperationKucoin } from '../../types/websockets/ws-api.js';
|
|
2
3
|
/** Should be one WS key per unique URL */
|
|
3
4
|
export declare const WS_KEY_MAP: {
|
|
4
5
|
readonly spotPublicV1: "spotPublicV1";
|
|
5
6
|
readonly spotPrivateV1: "spotPrivateV1";
|
|
6
7
|
readonly futuresPublicV1: "futuresPublicV1";
|
|
7
8
|
readonly futuresPrivateV1: "futuresPrivateV1";
|
|
9
|
+
readonly wsApiSpotV1: "wsApiSpotV1";
|
|
10
|
+
readonly wsApiFuturesV1: "wsApiFuturesV1";
|
|
8
11
|
};
|
|
9
12
|
/** This is used to differentiate between each of the available websocket streams */
|
|
10
13
|
export type WsKey = (typeof WS_KEY_MAP)[keyof typeof WS_KEY_MAP];
|
|
14
|
+
export type WSAPIWsKey = typeof WS_KEY_MAP.wsApiFuturesV1 | typeof WS_KEY_MAP.wsApiSpotV1;
|
|
11
15
|
/**
|
|
12
16
|
* Normalised internal format for a request (subscribe/unsubscribe/etc) on a topic, with optional parameters.
|
|
13
17
|
*
|
|
@@ -22,15 +26,17 @@ export interface WsTopicRequest<TWSTopic extends string = string, TWSPayload = a
|
|
|
22
26
|
* Conveniently allow users to request a topic either as string topics or objects (containing string topic + params)
|
|
23
27
|
*/
|
|
24
28
|
export type WsTopicRequestOrStringTopic<TWSTopic extends string, TWSPayload = any> = WsTopicRequest<TWSTopic, TWSPayload> | string;
|
|
25
|
-
export interface MessageEventLike {
|
|
26
|
-
target: WebSocket;
|
|
27
|
-
type: 'message';
|
|
28
|
-
data: string;
|
|
29
|
-
}
|
|
30
|
-
export declare function isMessageEvent(msg: unknown): msg is MessageEventLike;
|
|
31
29
|
/**
|
|
32
30
|
* #305: ws.terminate() is undefined in browsers.
|
|
33
31
|
* This only works in node.js, not in browsers.
|
|
34
32
|
* Does nothing if `ws` is undefined. Does nothing in browsers.
|
|
35
33
|
*/
|
|
36
34
|
export declare function safeTerminateWs(ws?: WebSocket | any, fallbackToClose?: boolean): boolean;
|
|
35
|
+
/**
|
|
36
|
+
* WS API promises are stored using a primary key. This key is constructed using
|
|
37
|
+
* properties found in every request & reply.
|
|
38
|
+
*
|
|
39
|
+
* The counterpart to this is in resolveEmittableEvents
|
|
40
|
+
*/
|
|
41
|
+
export declare function getPromiseRefForWSAPIRequest(wsKey: WsKey, requestEvent: WsRequestOperationKucoin<string>): string;
|
|
42
|
+
export declare function isWSAPIWsKey(wsKey: WsKey): wsKey is WSAPIWsKey;
|
|
@@ -1,22 +1,18 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.WS_KEY_MAP = void 0;
|
|
4
|
-
exports.isMessageEvent = isMessageEvent;
|
|
5
4
|
exports.safeTerminateWs = safeTerminateWs;
|
|
5
|
+
exports.getPromiseRefForWSAPIRequest = getPromiseRefForWSAPIRequest;
|
|
6
|
+
exports.isWSAPIWsKey = isWSAPIWsKey;
|
|
6
7
|
/** Should be one WS key per unique URL */
|
|
7
8
|
exports.WS_KEY_MAP = {
|
|
8
9
|
spotPublicV1: 'spotPublicV1',
|
|
9
10
|
spotPrivateV1: 'spotPrivateV1',
|
|
10
11
|
futuresPublicV1: 'futuresPublicV1',
|
|
11
12
|
futuresPrivateV1: 'futuresPrivateV1',
|
|
13
|
+
wsApiSpotV1: 'wsApiSpotV1',
|
|
14
|
+
wsApiFuturesV1: 'wsApiFuturesV1',
|
|
12
15
|
};
|
|
13
|
-
function isMessageEvent(msg) {
|
|
14
|
-
if (typeof msg !== 'object' || !msg) {
|
|
15
|
-
return false;
|
|
16
|
-
}
|
|
17
|
-
const message = msg;
|
|
18
|
-
return message['type'] === 'message' && typeof message['data'] === 'string';
|
|
19
|
-
}
|
|
20
16
|
/**
|
|
21
17
|
* #305: ws.terminate() is undefined in browsers.
|
|
22
18
|
* This only works in node.js, not in browsers.
|
|
@@ -35,4 +31,17 @@ function safeTerminateWs(ws, fallbackToClose) {
|
|
|
35
31
|
}
|
|
36
32
|
return false;
|
|
37
33
|
}
|
|
34
|
+
/**
|
|
35
|
+
* WS API promises are stored using a primary key. This key is constructed using
|
|
36
|
+
* properties found in every request & reply.
|
|
37
|
+
*
|
|
38
|
+
* The counterpart to this is in resolveEmittableEvents
|
|
39
|
+
*/
|
|
40
|
+
function getPromiseRefForWSAPIRequest(wsKey, requestEvent) {
|
|
41
|
+
const promiseRef = [wsKey, requestEvent.id].join('_');
|
|
42
|
+
return promiseRef;
|
|
43
|
+
}
|
|
44
|
+
function isWSAPIWsKey(wsKey) {
|
|
45
|
+
return (wsKey === exports.WS_KEY_MAP.wsApiFuturesV1 || wsKey === exports.WS_KEY_MAP.wsApiSpotV1);
|
|
46
|
+
}
|
|
38
47
|
//# sourceMappingURL=websocket-util.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"websocket-util.js","sourceRoot":"","sources":["../../../../src/lib/websocket/websocket-util.ts"],"names":[],"mappings":";;;
|
|
1
|
+
{"version":3,"file":"websocket-util.js","sourceRoot":"","sources":["../../../../src/lib/websocket/websocket-util.ts"],"names":[],"mappings":";;;AA+CA,0CAeC;AAQD,oEAMC;AAED,oCAIC;AA9ED,0CAA0C;AAC7B,QAAA,UAAU,GAAG;IACxB,YAAY,EAAE,cAAc;IAC5B,aAAa,EAAE,eAAe;IAC9B,eAAe,EAAE,iBAAiB;IAClC,gBAAgB,EAAE,kBAAkB;IACpC,WAAW,EAAE,aAAa;IAC1B,cAAc,EAAE,gBAAgB;CACxB,CAAC;AA8BX;;;;GAIG;AACH,SAAgB,eAAe,CAC7B,EAAoB,EACpB,eAAyB;IAEzB,IAAI,CAAC,EAAE,EAAE,CAAC;QACR,OAAO,KAAK,CAAC;IACf,CAAC;IACD,IAAI,OAAO,EAAE,CAAC,WAAW,CAAC,KAAK,UAAU,EAAE,CAAC;QAC1C,EAAE,CAAC,SAAS,EAAE,CAAC;QACf,OAAO,IAAI,CAAC;IACd,CAAC;SAAM,IAAI,eAAe,EAAE,CAAC;QAC3B,EAAE,CAAC,KAAK,EAAE,CAAC;IACb,CAAC;IAED,OAAO,KAAK,CAAC;AACf,CAAC;AAED;;;;;GAKG;AACH,SAAgB,4BAA4B,CAC1C,KAAY,EACZ,YAA8C;IAE9C,MAAM,UAAU,GAAG,CAAC,KAAK,EAAE,YAAY,CAAC,EAAE,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IACtD,OAAO,UAAU,CAAC;AACpB,CAAC;AAED,SAAgB,YAAY,CAAC,KAAY;IACvC,OAAO,CACL,KAAK,KAAK,kBAAU,CAAC,cAAc,IAAI,KAAK,KAAK,kBAAU,CAAC,WAAW,CACxE,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
import { WS_KEY_MAP, WsKey } from '../../lib/websocket/websocket-util.js';
|
|
2
|
+
import { BatchCancelOrdersRequest, Order } from '../request/futures.types.js';
|
|
3
|
+
import { SubmitHFMarginOrderRequest } from '../request/spot-margin-trading.js';
|
|
4
|
+
import { ModifyHFOrderRequest, SubmitHFOrderRequest } from '../request/spot-trading.js';
|
|
5
|
+
import { BatchCancelOrderResult, SubmitMultipleOrdersFuturesResponse } from '../response/futures.types.js';
|
|
6
|
+
import { MarginSubmitOrderV3Response } from '../response/spot-margin-trading.js';
|
|
7
|
+
import { SubmitHFOrderSyncResponse, SyncCancelHFOrderResponse } from '../response/spot-trading.js';
|
|
8
|
+
export type WsOperation = 'subscribe' | 'unsubscribe' | 'login' | 'access' | 'request' | 'ping';
|
|
9
|
+
export interface WsRequestOperation<TWSTopic extends string> {
|
|
10
|
+
id: number;
|
|
11
|
+
type: WsOperation;
|
|
12
|
+
topic: TWSTopic;
|
|
13
|
+
privateChannel: boolean;
|
|
14
|
+
response: boolean;
|
|
15
|
+
}
|
|
16
|
+
export type Exact<T> = {} & {
|
|
17
|
+
[K in keyof T]: T[K];
|
|
18
|
+
};
|
|
19
|
+
/**
|
|
20
|
+
* WS API commands (for sending requests via WS)
|
|
21
|
+
*/
|
|
22
|
+
export declare const WS_API_Operations: readonly ["ping", "spot.order", "spot.modify", "spot.cancel", "spot.sync_order", "spot.sync_cancel", "margin.order", "margin.cancel", "futures.order", "futures.cancel", "futures.multi_order", "futures.multi_cancel"];
|
|
23
|
+
export type WsAPIOperation = (typeof WS_API_Operations)[number];
|
|
24
|
+
export interface WsRequestOperationKucoin<TWSTopic extends string, TWSParams extends object = any> {
|
|
25
|
+
id: string;
|
|
26
|
+
op: WsOperation | WsAPIOperation;
|
|
27
|
+
args?: (TWSTopic | string | number)[] | TWSParams;
|
|
28
|
+
}
|
|
29
|
+
export interface WSAPIResponse<TResponseData extends object = object, TWSAPIOperation = WsAPIOperation> {
|
|
30
|
+
/** Auto-generated */
|
|
31
|
+
id: string;
|
|
32
|
+
op: TWSAPIOperation;
|
|
33
|
+
msg?: string;
|
|
34
|
+
code: '200000' | string;
|
|
35
|
+
data: TResponseData;
|
|
36
|
+
inTime: number;
|
|
37
|
+
outTime: number;
|
|
38
|
+
rateLimit?: {
|
|
39
|
+
limit: number;
|
|
40
|
+
reset: number;
|
|
41
|
+
remaining: number;
|
|
42
|
+
};
|
|
43
|
+
wsKey: WsKey;
|
|
44
|
+
isWSAPIResponse: boolean;
|
|
45
|
+
request?: any;
|
|
46
|
+
}
|
|
47
|
+
export interface WsAPIWsKeyTopicMap {
|
|
48
|
+
[WS_KEY_MAP.wsApiSpotV1]: WsAPIOperation;
|
|
49
|
+
[WS_KEY_MAP.wsApiFuturesV1]: WsAPIOperation;
|
|
50
|
+
}
|
|
51
|
+
export type WSAPICancelOrderRequest = {
|
|
52
|
+
symbol: string;
|
|
53
|
+
} & ({
|
|
54
|
+
orderId: string;
|
|
55
|
+
} | {
|
|
56
|
+
clientOid: string;
|
|
57
|
+
});
|
|
58
|
+
export interface WSAPIOrderResponse {
|
|
59
|
+
orderId: string;
|
|
60
|
+
clientOid: string;
|
|
61
|
+
}
|
|
62
|
+
export interface WsAPITopicRequestParamMap {
|
|
63
|
+
[key: string]: unknown;
|
|
64
|
+
subscribe: never;
|
|
65
|
+
unsubscribe: never;
|
|
66
|
+
login: never;
|
|
67
|
+
access: never;
|
|
68
|
+
request: never;
|
|
69
|
+
ping: void;
|
|
70
|
+
'spot.order': SubmitHFOrderRequest;
|
|
71
|
+
'margin.order': SubmitHFMarginOrderRequest;
|
|
72
|
+
'futures.order': Order;
|
|
73
|
+
'spot.cancel': WSAPICancelOrderRequest;
|
|
74
|
+
'margin.cancel': WSAPICancelOrderRequest;
|
|
75
|
+
'futures.cancel': {
|
|
76
|
+
orderId: string;
|
|
77
|
+
} | {
|
|
78
|
+
clientOid: string;
|
|
79
|
+
symbol: string;
|
|
80
|
+
};
|
|
81
|
+
'futures.multi_cancel': BatchCancelOrdersRequest;
|
|
82
|
+
'futures.multi_order': Order[];
|
|
83
|
+
'spot.sync_order': SubmitHFOrderRequest;
|
|
84
|
+
'spot.modify': ModifyHFOrderRequest;
|
|
85
|
+
'spot.sync_cancel': WSAPICancelOrderRequest;
|
|
86
|
+
}
|
|
87
|
+
export interface WsAPITopicResponseMap {
|
|
88
|
+
[key: string]: unknown;
|
|
89
|
+
subscribe: never;
|
|
90
|
+
unsubscribe: never;
|
|
91
|
+
login: never;
|
|
92
|
+
access: never;
|
|
93
|
+
request: never;
|
|
94
|
+
ping: unknown;
|
|
95
|
+
'spot.order': WSAPIResponse<WSAPIOrderResponse>;
|
|
96
|
+
'margin.order': WSAPIResponse<MarginSubmitOrderV3Response>;
|
|
97
|
+
'futures.order': WSAPIResponse<WSAPIOrderResponse>;
|
|
98
|
+
'spot.cancel': WSAPIResponse<WSAPIOrderResponse>;
|
|
99
|
+
'margin.cancel': WSAPIResponse<WSAPIOrderResponse>;
|
|
100
|
+
'futures.cancel': WSAPIResponse<{
|
|
101
|
+
cancelledOrderIds: string[];
|
|
102
|
+
} | {
|
|
103
|
+
clientOid: string;
|
|
104
|
+
}>;
|
|
105
|
+
'futures.multi_cancel': WSAPIResponse<BatchCancelOrderResult[]>;
|
|
106
|
+
'futures.multi_order': WSAPIResponse<SubmitMultipleOrdersFuturesResponse[]>;
|
|
107
|
+
'spot.sync_order': WSAPIResponse<SubmitHFOrderSyncResponse>;
|
|
108
|
+
'spot.modify': WSAPIResponse<{
|
|
109
|
+
newOrderId: string;
|
|
110
|
+
clientOid: string;
|
|
111
|
+
}>;
|
|
112
|
+
'spot.sync_cancel': WSAPIResponse<SyncCancelHFOrderResponse>;
|
|
113
|
+
}
|
|
114
|
+
export interface WSAPIAuthenticationRequestFromServer {
|
|
115
|
+
timestamp: number;
|
|
116
|
+
sessionId: string;
|
|
117
|
+
}
|
|
118
|
+
export interface WSAPIAuthenticationConfirmedFromServer {
|
|
119
|
+
pingInterval: number;
|
|
120
|
+
sessionId: string;
|
|
121
|
+
pingTimeout: number;
|
|
122
|
+
data: 'welcome';
|
|
123
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.WS_API_Operations = void 0;
|
|
4
|
+
const websocket_util_js_1 = require("../../lib/websocket/websocket-util.js");
|
|
5
|
+
/**
|
|
6
|
+
* WS API commands (for sending requests via WS)
|
|
7
|
+
*/
|
|
8
|
+
exports.WS_API_Operations = [
|
|
9
|
+
'ping',
|
|
10
|
+
'spot.order',
|
|
11
|
+
'spot.modify',
|
|
12
|
+
'spot.cancel',
|
|
13
|
+
'spot.sync_order',
|
|
14
|
+
'spot.sync_cancel',
|
|
15
|
+
'margin.order',
|
|
16
|
+
'margin.cancel',
|
|
17
|
+
'futures.order',
|
|
18
|
+
'futures.cancel',
|
|
19
|
+
'futures.multi_order',
|
|
20
|
+
'futures.multi_cancel',
|
|
21
|
+
];
|
|
22
|
+
//# sourceMappingURL=ws-api.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ws-api.js","sourceRoot":"","sources":["../../../../src/types/websockets/ws-api.ts"],"names":[],"mappings":";;;AAAA,6EAA0E;AAyC1E;;GAEG;AACU,QAAA,iBAAiB,GAAG;IAC/B,MAAM;IACN,YAAY;IACZ,aAAa;IACb,aAAa;IACb,iBAAiB;IACjB,kBAAkB;IAClB,cAAc;IACd,eAAe;IACf,eAAe;IACf,gBAAgB;IAChB,qBAAqB;IACrB,sBAAsB;CACd,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export interface WsDataEvent<TData = any, TWSKey = string> {
|
|
2
|
+
data: TData;
|
|
3
|
+
table: string;
|
|
4
|
+
wsKey: TWSKey;
|
|
5
|
+
}
|
|
6
|
+
export interface MessageEventLike {
|
|
7
|
+
target: WebSocket;
|
|
8
|
+
type: 'message';
|
|
9
|
+
data: string;
|
|
10
|
+
}
|
|
11
|
+
export declare function isMessageEvent(msg: unknown): msg is MessageEventLike;
|