@sisense/sdk-pivot-query-client 2.17.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.
Files changed (189) hide show
  1. package/LICENSE.md +35 -0
  2. package/README.md +2 -0
  3. package/dist/__test-helpers__/testUtils.d.ts +30 -0
  4. package/dist/__test-helpers__/testUtils.js +89 -0
  5. package/dist/builders/index.d.ts +2 -0
  6. package/dist/builders/index.js +2 -0
  7. package/dist/builders/pivot-data-builder.d.ts +34 -0
  8. package/dist/builders/pivot-data-builder.js +182 -0
  9. package/dist/builders/socket-builder.d.ts +18 -0
  10. package/dist/builders/socket-builder.js +72 -0
  11. package/dist/cjs/__test-helpers__/testUtils.d.ts +30 -0
  12. package/dist/cjs/__test-helpers__/testUtils.js +104 -0
  13. package/dist/cjs/builders/index.d.ts +2 -0
  14. package/dist/cjs/builders/index.js +7 -0
  15. package/dist/cjs/builders/pivot-data-builder.d.ts +34 -0
  16. package/dist/cjs/builders/pivot-data-builder.js +186 -0
  17. package/dist/cjs/builders/socket-builder.d.ts +18 -0
  18. package/dist/cjs/builders/socket-builder.js +79 -0
  19. package/dist/cjs/data-handling/DataService.d.ts +672 -0
  20. package/dist/cjs/data-handling/DataService.js +1364 -0
  21. package/dist/cjs/data-handling/DivergenceComparator.d.ts +7 -0
  22. package/dist/cjs/data-handling/DivergenceComparator.js +20 -0
  23. package/dist/cjs/data-handling/constants.d.ts +44 -0
  24. package/dist/cjs/data-handling/constants.js +43 -0
  25. package/dist/cjs/data-handling/index.d.ts +3 -0
  26. package/dist/cjs/data-handling/index.js +23 -0
  27. package/dist/cjs/data-handling/types.d.ts +104 -0
  28. package/dist/cjs/data-handling/types.js +2 -0
  29. package/dist/cjs/data-handling/utils/createPivotTreeNode.d.ts +13 -0
  30. package/dist/cjs/data-handling/utils/createPivotTreeNode.js +21 -0
  31. package/dist/cjs/data-handling/utils/index.d.ts +4 -0
  32. package/dist/cjs/data-handling/utils/index.js +14 -0
  33. package/dist/cjs/data-handling/utils/jaqlProcessor.d.ts +122 -0
  34. package/dist/cjs/data-handling/utils/jaqlProcessor.js +661 -0
  35. package/dist/cjs/data-handling/utils/pivotTransforms.d.ts +74 -0
  36. package/dist/cjs/data-handling/utils/pivotTransforms.js +373 -0
  37. package/dist/cjs/data-handling/utils/plugins/PluginService.d.ts +135 -0
  38. package/dist/cjs/data-handling/utils/plugins/PluginService.js +383 -0
  39. package/dist/cjs/data-handling/utils/plugins/getters.d.ts +23 -0
  40. package/dist/cjs/data-handling/utils/plugins/getters.js +70 -0
  41. package/dist/cjs/data-handling/utils/plugins/types.d.ts +75 -0
  42. package/dist/cjs/data-handling/utils/plugins/types.js +2 -0
  43. package/dist/cjs/data-handling/utils/plugins/validator.d.ts +13 -0
  44. package/dist/cjs/data-handling/utils/plugins/validator.js +169 -0
  45. package/dist/cjs/data-load/AbstractDataLoadService.d.ts +256 -0
  46. package/dist/cjs/data-load/AbstractDataLoadService.js +473 -0
  47. package/dist/cjs/data-load/DataLoadService.d.ts +63 -0
  48. package/dist/cjs/data-load/DataLoadService.js +152 -0
  49. package/dist/cjs/data-load/SisenseDataLoadService.d.ts +44 -0
  50. package/dist/cjs/data-load/SisenseDataLoadService.js +87 -0
  51. package/dist/cjs/data-load/TestDataLoadService.d.ts +27 -0
  52. package/dist/cjs/data-load/TestDataLoadService.js +76 -0
  53. package/dist/cjs/data-load/constants.d.ts +13 -0
  54. package/dist/cjs/data-load/constants.js +28 -0
  55. package/dist/cjs/data-load/index.d.ts +6 -0
  56. package/dist/cjs/data-load/index.js +14 -0
  57. package/dist/cjs/data-load/sockets/SisenseSocket.d.ts +81 -0
  58. package/dist/cjs/data-load/sockets/SisenseSocket.js +162 -0
  59. package/dist/cjs/data-load/sockets/TestSocket.d.ts +61 -0
  60. package/dist/cjs/data-load/sockets/TestSocket.js +90 -0
  61. package/dist/cjs/data-load/sockets/helpers.d.ts +4 -0
  62. package/dist/cjs/data-load/sockets/helpers.js +27 -0
  63. package/dist/cjs/data-load/sockets/index.d.ts +2 -0
  64. package/dist/cjs/data-load/sockets/index.js +8 -0
  65. package/dist/cjs/data-load/types.d.ts +90 -0
  66. package/dist/cjs/data-load/types.js +2 -0
  67. package/dist/cjs/errors/LoadingCanceledError.d.ts +7 -0
  68. package/dist/cjs/errors/LoadingCanceledError.js +24 -0
  69. package/dist/cjs/errors/index.d.ts +1 -0
  70. package/dist/cjs/errors/index.js +6 -0
  71. package/dist/cjs/index.d.ts +17 -0
  72. package/dist/cjs/index.js +32 -0
  73. package/dist/cjs/package.json +12 -0
  74. package/dist/cjs/pivot-query-client.d.ts +13 -0
  75. package/dist/cjs/pivot-query-client.js +26 -0
  76. package/dist/cjs/tree-structure/AbstractTreeService.d.ts +308 -0
  77. package/dist/cjs/tree-structure/AbstractTreeService.js +716 -0
  78. package/dist/cjs/tree-structure/HeaderTreeService.d.ts +180 -0
  79. package/dist/cjs/tree-structure/HeaderTreeService.js +280 -0
  80. package/dist/cjs/tree-structure/TreeCellMap.d.ts +104 -0
  81. package/dist/cjs/tree-structure/TreeCellMap.js +145 -0
  82. package/dist/cjs/tree-structure/TreeService.d.ts +8 -0
  83. package/dist/cjs/tree-structure/TreeService.js +12 -0
  84. package/dist/cjs/tree-structure/constants.d.ts +6 -0
  85. package/dist/cjs/tree-structure/constants.js +10 -0
  86. package/dist/cjs/tree-structure/index.d.ts +5 -0
  87. package/dist/cjs/tree-structure/index.js +10 -0
  88. package/dist/cjs/tree-structure/types.d.ts +93 -0
  89. package/dist/cjs/tree-structure/types.js +2 -0
  90. package/dist/cjs/tree-structure/utils/index.d.ts +1 -0
  91. package/dist/cjs/tree-structure/utils/index.js +9 -0
  92. package/dist/cjs/tree-structure/utils/treeNode.d.ts +147 -0
  93. package/dist/cjs/tree-structure/utils/treeNode.js +534 -0
  94. package/dist/cjs/utils/array.d.ts +13 -0
  95. package/dist/cjs/utils/array.js +25 -0
  96. package/dist/cjs/utils/cloneObject.d.ts +30 -0
  97. package/dist/cjs/utils/cloneObject.js +225 -0
  98. package/dist/cjs/utils/index.d.ts +3 -0
  99. package/dist/cjs/utils/index.js +9 -0
  100. package/dist/cjs/utils/throttle.d.ts +12 -0
  101. package/dist/cjs/utils/throttle.js +39 -0
  102. package/dist/cjs/utils/types.d.ts +12 -0
  103. package/dist/cjs/utils/types.js +2 -0
  104. package/dist/data-handling/DataService.d.ts +672 -0
  105. package/dist/data-handling/DataService.js +1357 -0
  106. package/dist/data-handling/DivergenceComparator.d.ts +7 -0
  107. package/dist/data-handling/DivergenceComparator.js +16 -0
  108. package/dist/data-handling/constants.d.ts +44 -0
  109. package/dist/data-handling/constants.js +40 -0
  110. package/dist/data-handling/index.d.ts +3 -0
  111. package/dist/data-handling/index.js +4 -0
  112. package/dist/data-handling/types.d.ts +104 -0
  113. package/dist/data-handling/types.js +1 -0
  114. package/dist/data-handling/utils/createPivotTreeNode.d.ts +13 -0
  115. package/dist/data-handling/utils/createPivotTreeNode.js +17 -0
  116. package/dist/data-handling/utils/index.d.ts +4 -0
  117. package/dist/data-handling/utils/index.js +4 -0
  118. package/dist/data-handling/utils/jaqlProcessor.d.ts +122 -0
  119. package/dist/data-handling/utils/jaqlProcessor.js +621 -0
  120. package/dist/data-handling/utils/pivotTransforms.d.ts +74 -0
  121. package/dist/data-handling/utils/pivotTransforms.js +335 -0
  122. package/dist/data-handling/utils/plugins/PluginService.d.ts +135 -0
  123. package/dist/data-handling/utils/plugins/PluginService.js +379 -0
  124. package/dist/data-handling/utils/plugins/getters.d.ts +23 -0
  125. package/dist/data-handling/utils/plugins/getters.js +65 -0
  126. package/dist/data-handling/utils/plugins/types.d.ts +75 -0
  127. package/dist/data-handling/utils/plugins/types.js +1 -0
  128. package/dist/data-handling/utils/plugins/validator.d.ts +13 -0
  129. package/dist/data-handling/utils/plugins/validator.js +165 -0
  130. package/dist/data-load/AbstractDataLoadService.d.ts +256 -0
  131. package/dist/data-load/AbstractDataLoadService.js +466 -0
  132. package/dist/data-load/DataLoadService.d.ts +63 -0
  133. package/dist/data-load/DataLoadService.js +148 -0
  134. package/dist/data-load/SisenseDataLoadService.d.ts +44 -0
  135. package/dist/data-load/SisenseDataLoadService.js +83 -0
  136. package/dist/data-load/TestDataLoadService.d.ts +27 -0
  137. package/dist/data-load/TestDataLoadService.js +69 -0
  138. package/dist/data-load/constants.d.ts +13 -0
  139. package/dist/data-load/constants.js +25 -0
  140. package/dist/data-load/index.d.ts +6 -0
  141. package/dist/data-load/index.js +6 -0
  142. package/dist/data-load/sockets/SisenseSocket.d.ts +81 -0
  143. package/dist/data-load/sockets/SisenseSocket.js +155 -0
  144. package/dist/data-load/sockets/TestSocket.d.ts +61 -0
  145. package/dist/data-load/sockets/TestSocket.js +83 -0
  146. package/dist/data-load/sockets/helpers.d.ts +4 -0
  147. package/dist/data-load/sockets/helpers.js +23 -0
  148. package/dist/data-load/sockets/index.d.ts +2 -0
  149. package/dist/data-load/sockets/index.js +3 -0
  150. package/dist/data-load/types.d.ts +90 -0
  151. package/dist/data-load/types.js +1 -0
  152. package/dist/errors/LoadingCanceledError.d.ts +7 -0
  153. package/dist/errors/LoadingCanceledError.js +20 -0
  154. package/dist/errors/index.d.ts +1 -0
  155. package/dist/errors/index.js +2 -0
  156. package/dist/index.d.ts +17 -0
  157. package/dist/index.js +9 -0
  158. package/dist/pivot-query-client.d.ts +13 -0
  159. package/dist/pivot-query-client.js +22 -0
  160. package/dist/tree-structure/AbstractTreeService.d.ts +308 -0
  161. package/dist/tree-structure/AbstractTreeService.js +712 -0
  162. package/dist/tree-structure/HeaderTreeService.d.ts +180 -0
  163. package/dist/tree-structure/HeaderTreeService.js +276 -0
  164. package/dist/tree-structure/TreeCellMap.d.ts +104 -0
  165. package/dist/tree-structure/TreeCellMap.js +141 -0
  166. package/dist/tree-structure/TreeService.d.ts +8 -0
  167. package/dist/tree-structure/TreeService.js +8 -0
  168. package/dist/tree-structure/constants.d.ts +6 -0
  169. package/dist/tree-structure/constants.js +7 -0
  170. package/dist/tree-structure/index.d.ts +5 -0
  171. package/dist/tree-structure/index.js +4 -0
  172. package/dist/tree-structure/types.d.ts +93 -0
  173. package/dist/tree-structure/types.js +1 -0
  174. package/dist/tree-structure/utils/index.d.ts +1 -0
  175. package/dist/tree-structure/utils/index.js +1 -0
  176. package/dist/tree-structure/utils/treeNode.d.ts +147 -0
  177. package/dist/tree-structure/utils/treeNode.js +515 -0
  178. package/dist/tsconfig.prod.cjs.tsbuildinfo +1 -0
  179. package/dist/utils/array.d.ts +13 -0
  180. package/dist/utils/array.js +21 -0
  181. package/dist/utils/cloneObject.d.ts +30 -0
  182. package/dist/utils/cloneObject.js +221 -0
  183. package/dist/utils/index.d.ts +3 -0
  184. package/dist/utils/index.js +3 -0
  185. package/dist/utils/throttle.d.ts +12 -0
  186. package/dist/utils/throttle.js +35 -0
  187. package/dist/utils/types.d.ts +12 -0
  188. package/dist/utils/types.js +1 -0
  189. package/package.json +61 -0
@@ -0,0 +1,44 @@
1
+ /// <reference types="node" resolution-mode="require"/>
2
+ /// <reference types="node" resolution-mode="require"/>
3
+ import EventEmitter from 'events';
4
+ import { DataLoadService } from './DataLoadService.js';
5
+ import { DataLoadServiceI, SocketI } from './types.js';
6
+ declare type Options = {
7
+ socketRegisterCheckInterval?: number;
8
+ };
9
+ /**
10
+ * Initiate single socket connection and creates new PivotDataSource for each JAQL request
11
+ */
12
+ export declare class SisenseDataLoadService extends DataLoadService implements DataLoadServiceI {
13
+ /**
14
+ * @private
15
+ */
16
+ options: Options;
17
+ /**
18
+ * @private
19
+ */
20
+ registrationWaitTimer?: NodeJS.Timeout;
21
+ /**
22
+ * @private
23
+ *
24
+ * onMessage remove listeners callback
25
+ */
26
+ onMessageCancels: Array<Function | undefined>;
27
+ constructor(socket?: SocketI, events?: EventEmitter, options?: Options);
28
+ destroy(): void;
29
+ /**
30
+ * Start data loading from the server
31
+ *
32
+ * @returns {void}
33
+ * @private
34
+ */
35
+ loadFromServer(): void;
36
+ /**
37
+ * Wait for socket connection and registration
38
+ *
39
+ * @returns {Promise<*>} - wait promise
40
+ * @private
41
+ */
42
+ waitForSocketReady(): Promise<any>;
43
+ }
44
+ export default SisenseDataLoadService;
@@ -0,0 +1,83 @@
1
+ import { v4 as uuid } from 'uuid';
2
+ import { MessageType } from './constants.js';
3
+ import { DataLoadService } from './DataLoadService.js';
4
+ /**
5
+ * Initiate single socket connection and creates new PivotDataSource for each JAQL request
6
+ */
7
+ export class SisenseDataLoadService extends DataLoadService {
8
+ constructor(socket, events, options = {}) {
9
+ super(socket, events);
10
+ /**
11
+ * @private
12
+ *
13
+ * onMessage remove listeners callback
14
+ */
15
+ this.onMessageCancels = [];
16
+ this.options = options;
17
+ }
18
+ destroy() {
19
+ super.destroy();
20
+ if (this.onMessageCancels.length) {
21
+ this.onMessageCancels.forEach((onMessageCancel) => {
22
+ if (onMessageCancel) {
23
+ onMessageCancel();
24
+ }
25
+ });
26
+ this.onMessageCancels.length = 0;
27
+ }
28
+ }
29
+ /**
30
+ * Start data loading from the server
31
+ *
32
+ * @returns {void}
33
+ * @private
34
+ */
35
+ loadFromServer() {
36
+ // eslint-disable-next-line promise/catch-or-return
37
+ this.waitForSocketReady().then(() => {
38
+ const queryJaql = Object.assign({ queryGuid: uuid() }, this.jaql);
39
+ const { queryGuid } = queryJaql;
40
+ if (this.onMessageCancels.length) {
41
+ this.onMessageCancels.forEach((onMessageCancel) => {
42
+ if (onMessageCancel) {
43
+ onMessageCancel();
44
+ }
45
+ });
46
+ this.onMessageCancels.length = 0;
47
+ }
48
+ Object.values(MessageType).forEach((mType) => {
49
+ // TODO: misnomer??? It should be onMessageHandle
50
+ const onMessageCancel = this.socket.onMessage(mType, queryGuid, (type, data) => {
51
+ this.notifyAboutDataChunk(type, data);
52
+ });
53
+ this.onMessageCancels.push(onMessageCancel);
54
+ });
55
+ this.socket.send('pivot', queryJaql);
56
+ });
57
+ }
58
+ /**
59
+ * Wait for socket connection and registration
60
+ *
61
+ * @returns {Promise<*>} - wait promise
62
+ * @private
63
+ */
64
+ waitForSocketReady() {
65
+ if (this.socket.isReady()) {
66
+ return Promise.resolve();
67
+ }
68
+ return new Promise((resolve) => {
69
+ const { socketRegisterCheckInterval = 100 } = this.options;
70
+ if (this.registrationWaitTimer) {
71
+ clearInterval(this.registrationWaitTimer);
72
+ }
73
+ const checkSocketReady = () => {
74
+ if (this.socket.isReady()) {
75
+ clearInterval(this.registrationWaitTimer);
76
+ resolve();
77
+ }
78
+ };
79
+ this.registrationWaitTimer = setInterval(checkSocketReady, socketRegisterCheckInterval);
80
+ });
81
+ }
82
+ }
83
+ export default SisenseDataLoadService;
@@ -0,0 +1,27 @@
1
+ /// <reference types="node" resolution-mode="require"/>
2
+ import EventEmitter from 'events';
3
+ import { DataLoadServiceI, JaqlRequest } from './types.js';
4
+ export declare class TestDataLoadService implements DataLoadServiceI {
5
+ events: EventEmitter;
6
+ data?: JaqlRequest;
7
+ delegatedLoadService?: DataLoadServiceI;
8
+ constructor(url: string, events?: EventEmitter);
9
+ destroy(): void;
10
+ clone(): DataLoadServiceI;
11
+ load(jaql: JaqlRequest): Promise<any>;
12
+ cancelQuery(): Promise<void>;
13
+ clear(): void;
14
+ getJaql(): JaqlRequest | undefined;
15
+ isSingleRowTree(): boolean;
16
+ getTotalItemsCount(): number;
17
+ delegate(loadService: DataLoadServiceI): void;
18
+ on(eventName: string, callback: (payload: any) => void): void;
19
+ off(eventName: string, callback: (payload: any) => void): void;
20
+ offAll(eventName: string): void;
21
+ listenerCount(eventName: string): number;
22
+ emit(eventName: string, ...rest: Array<any>): void;
23
+ isFormattingChanges(jaql?: JaqlRequest): boolean;
24
+ hasData(): boolean;
25
+ hasError(): boolean;
26
+ }
27
+ export default TestDataLoadService;
@@ -0,0 +1,69 @@
1
+ /* eslint-disable class-methods-use-this */
2
+ import EventEmitter from 'events';
3
+ export class TestDataLoadService {
4
+ constructor(url, events) {
5
+ this.delegatedLoadService = undefined;
6
+ this.events = events || new EventEmitter();
7
+ }
8
+ destroy() {
9
+ this.data = undefined;
10
+ }
11
+ clone() {
12
+ throw new Error(`"TestDataLoadService.clone" should not be called`);
13
+ }
14
+ load(jaql) {
15
+ this.data = jaql;
16
+ return Promise.resolve(null);
17
+ }
18
+ cancelQuery() {
19
+ return Promise.resolve();
20
+ }
21
+ clear() {
22
+ this.data = undefined;
23
+ }
24
+ getJaql() {
25
+ return this.data;
26
+ }
27
+ isSingleRowTree() {
28
+ return !this.data;
29
+ }
30
+ getTotalItemsCount() {
31
+ return this && 0;
32
+ }
33
+ delegate(loadService) {
34
+ this.delegatedLoadService = loadService;
35
+ }
36
+ on(eventName, callback) {
37
+ this.events.on(eventName, callback);
38
+ }
39
+ off(eventName, callback) {
40
+ this.events.removeListener(eventName, callback);
41
+ }
42
+ offAll(eventName) {
43
+ this.events.removeAllListeners(eventName);
44
+ }
45
+ listenerCount(eventName) {
46
+ return this.events.listenerCount(eventName);
47
+ }
48
+ emit(eventName, ...rest) {
49
+ this.events.emit(eventName, ...rest);
50
+ }
51
+ isFormattingChanges(jaql) {
52
+ return jaql ? true : !!this;
53
+ }
54
+ // applyFormattingChanges(jaql?: JaqlRequest): Promise<DataLoadServiceI> {
55
+ // const res = jaql ? this : this;
56
+ // return Promise.resolve(res);
57
+ // }
58
+ //
59
+ // checkSorting(): Promise<void> {
60
+ // return this && Promise.resolve();
61
+ // }
62
+ hasData() {
63
+ return this && true;
64
+ }
65
+ hasError() {
66
+ return this && false;
67
+ }
68
+ }
69
+ export default TestDataLoadService;
@@ -0,0 +1,13 @@
1
+ export declare const MessageType: {
2
+ HEADERS: string;
3
+ METADATA: string;
4
+ DATA: string;
5
+ GRAND: string;
6
+ FINISH: string;
7
+ ERROR: string;
8
+ TOTAL_ROWS: string;
9
+ DATA_FINISH: string;
10
+ DATABARS: string;
11
+ RANGE_MIN_MAX: string;
12
+ };
13
+ export declare const MESSAGES_ORDER: string[];
@@ -0,0 +1,25 @@
1
+ // Message type for each of the data chunks
2
+ export const MessageType = {
3
+ HEADERS: 'headers',
4
+ METADATA: 'metadata',
5
+ DATA: 'data',
6
+ GRAND: 'grand',
7
+ FINISH: 'finish',
8
+ ERROR: 'error',
9
+ TOTAL_ROWS: 'totalRows',
10
+ DATA_FINISH: 'dataFinish',
11
+ DATABARS: 'dataBars',
12
+ RANGE_MIN_MAX: 'rangeMinMax',
13
+ };
14
+ export const MESSAGES_ORDER = [
15
+ MessageType.ERROR,
16
+ MessageType.HEADERS,
17
+ MessageType.GRAND,
18
+ MessageType.METADATA,
19
+ MessageType.DATA,
20
+ MessageType.DATA_FINISH,
21
+ MessageType.TOTAL_ROWS,
22
+ MessageType.DATABARS,
23
+ MessageType.RANGE_MIN_MAX,
24
+ MessageType.FINISH,
25
+ ];
@@ -0,0 +1,6 @@
1
+ export { AbstractDataLoadService } from './AbstractDataLoadService.js';
2
+ export { DataLoadService } from './DataLoadService.js';
3
+ export { SisenseDataLoadService } from './SisenseDataLoadService.js';
4
+ export { TestDataLoadService } from './TestDataLoadService.js';
5
+ export { SisenseSocket } from './sockets/SisenseSocket.js';
6
+ export { type MeasurePath } from './types.js';
@@ -0,0 +1,6 @@
1
+ /* eslint-disable import/prefer-default-export */
2
+ export { AbstractDataLoadService } from './AbstractDataLoadService.js';
3
+ export { DataLoadService } from './DataLoadService.js';
4
+ export { SisenseDataLoadService } from './SisenseDataLoadService.js';
5
+ export { TestDataLoadService } from './TestDataLoadService.js';
6
+ export { SisenseSocket } from './sockets/SisenseSocket.js';
@@ -0,0 +1,81 @@
1
+ import { SocketI, SocketQueryOptions } from '../types.js';
2
+ export declare class SisenseSocket implements SocketI {
3
+ /**
4
+ @private */
5
+ socket: SocketIOClient.Socket;
6
+ private isRegistered;
7
+ private isListening;
8
+ /**
9
+ @private */
10
+ onMessageCallback?: (type: string, data: any) => void;
11
+ /**
12
+ * Creates a new SisenseSocket instance.
13
+ *
14
+ * @param data - Either a URL string or an existing SocketIOClient.Socket instance
15
+ * @param query - Socket query options for authentication
16
+ * @param namespace - Optional socket.io namespace to connect to (e.g., 'pivot2')
17
+ */
18
+ constructor(data: string | SocketIOClient.Socket, query: SocketQueryOptions, namespace?: string);
19
+ /**
20
+ * Subscribes on socket readiness events
21
+ */
22
+ subcribeOnSocketReadiness(): void;
23
+ /**
24
+ * Checks if socket is ready for sending messages or not
25
+ *
26
+ * @returns {boolean} - true - ready
27
+ */
28
+ isReady(): boolean;
29
+ /**
30
+ * Attach event handler
31
+ *
32
+ * @param {string} event - event name
33
+ * @param {Function} cb - handler function
34
+ * @returns {void}
35
+ */
36
+ on(event: string, cb: Function): void;
37
+ /**
38
+ * Detach event handler
39
+ *
40
+ * @param {string} event - event name
41
+ * @param {Function} cb - handler function
42
+ * @returns {void}
43
+ */
44
+ off(event: string, cb: Function): void;
45
+ /**
46
+ * Send message via socket
47
+ *
48
+ * @param {string} event - message name
49
+ * @param {Array<any>} args - arguments
50
+ * @param {Array<any>} args.0 - message data
51
+ * @returns {void}
52
+ */
53
+ send(event: string, ...args: any[]): void;
54
+ /**
55
+ * Specific message handler
56
+ *
57
+ * @param {string} type - message type
58
+ * @param {string} subType - message subtype (query ID)
59
+ * @param {Function} callback - handler function
60
+ * @returns {Function} - unsubscribe function
61
+ */
62
+ onMessage(type: string, subType: string, callback: (type: string, data: any) => void): () => void;
63
+ /**
64
+ * Emulate receiving message from socket
65
+ *
66
+ * @param {string} event - message type
67
+ * @param {any} data - message data
68
+ * @returns {void}
69
+ */
70
+ trigger(event: string, data: any): any;
71
+ /**
72
+ * Creates and configures a new socket.io connection.
73
+ *
74
+ * @param url - Base URL of the Sisense instance
75
+ * @param query - Socket query options for authentication
76
+ * @param namespace - Optional socket.io namespace to connect to (e.g., 'pivot2')
77
+ * @returns Configured SocketIOClient.Socket instance
78
+ */
79
+ static createNewSocket(url: string, query: SocketQueryOptions, namespace?: string): SocketIOClient.Socket;
80
+ }
81
+ export default SisenseSocket;
@@ -0,0 +1,155 @@
1
+ /* eslint-disable @typescript-eslint/ban-types */
2
+ import { normalizeUrl } from '@sisense/sdk-common';
3
+ import io from 'socket.io-client';
4
+ import { getCsrfResponseData } from './helpers.js';
5
+ export class SisenseSocket {
6
+ /**
7
+ * Creates a new SisenseSocket instance.
8
+ *
9
+ * @param data - Either a URL string or an existing SocketIOClient.Socket instance
10
+ * @param query - Socket query options for authentication
11
+ * @param namespace - Optional socket.io namespace to connect to (e.g., 'pivot2')
12
+ */
13
+ constructor(data, query, namespace) {
14
+ this.isRegistered = false;
15
+ this.isListening = false;
16
+ if (typeof data === 'string') {
17
+ this.socket = SisenseSocket.createNewSocket(data, query, namespace);
18
+ this.subcribeOnSocketReadiness();
19
+ }
20
+ else {
21
+ this.socket = data;
22
+ }
23
+ }
24
+ /**
25
+ * Subscribes on socket readiness events
26
+ */
27
+ subcribeOnSocketReadiness() {
28
+ this.socket.on('register', () => {
29
+ this.isRegistered = true;
30
+ });
31
+ this.socket.on('listen', () => {
32
+ this.isListening = true;
33
+ });
34
+ }
35
+ /**
36
+ * Checks if socket is ready for sending messages or not
37
+ *
38
+ * @returns {boolean} - true - ready
39
+ */
40
+ isReady() {
41
+ // return this.socket.registeredInSisense;
42
+ return this.isRegistered && this.isListening;
43
+ }
44
+ /**
45
+ * Attach event handler
46
+ *
47
+ * @param {string} event - event name
48
+ * @param {Function} cb - handler function
49
+ * @returns {void}
50
+ */
51
+ on(event, cb) {
52
+ this.socket.on(event, cb);
53
+ }
54
+ /**
55
+ * Detach event handler
56
+ *
57
+ * @param {string} event - event name
58
+ * @param {Function} cb - handler function
59
+ * @returns {void}
60
+ */
61
+ off(event, cb) {
62
+ this.socket.off(event, cb);
63
+ }
64
+ /**
65
+ * Send message via socket
66
+ *
67
+ * @param {string} event - message name
68
+ * @param {Array<any>} args - arguments
69
+ * @param {Array<any>} args.0 - message data
70
+ * @returns {void}
71
+ */
72
+ send(event, ...args) {
73
+ const data = args[0];
74
+ this.socket.emit(event, JSON.stringify(data));
75
+ }
76
+ /**
77
+ * Specific message handler
78
+ *
79
+ * @param {string} type - message type
80
+ * @param {string} subType - message subtype (query ID)
81
+ * @param {Function} callback - handler function
82
+ * @returns {Function} - unsubscribe function
83
+ */
84
+ onMessage(type, subType, callback) {
85
+ this.onMessageCallback = callback;
86
+ const eventType = type || '';
87
+ const eventSubType = subType || '';
88
+ const eventName = eventSubType ? `${eventType}-${eventSubType}` : eventType;
89
+ const handler = (event) => {
90
+ let data = null;
91
+ try {
92
+ data = JSON.parse(event);
93
+ }
94
+ catch (err) {
95
+ throw new Error('Error parsing response message');
96
+ }
97
+ callback(eventType, data);
98
+ };
99
+ this.on(eventName, handler);
100
+ return () => {
101
+ this.off(eventName, handler);
102
+ };
103
+ }
104
+ /**
105
+ * Emulate receiving message from socket
106
+ *
107
+ * @param {string} event - message type
108
+ * @param {any} data - message data
109
+ * @returns {void}
110
+ */
111
+ trigger(event, data) {
112
+ if (this.onMessageCallback) {
113
+ this.onMessageCallback(event, data);
114
+ }
115
+ }
116
+ /**
117
+ * Creates and configures a new socket.io connection.
118
+ *
119
+ * @param url - Base URL of the Sisense instance
120
+ * @param query - Socket query options for authentication
121
+ * @param namespace - Optional socket.io namespace to connect to (e.g., 'pivot2')
122
+ * @returns Configured SocketIOClient.Socket instance
123
+ */
124
+ static createNewSocket(url, query, namespace) {
125
+ const gatewayUrl = new URL('./gateway', new URL(normalizeUrl(url)));
126
+ const uri = gatewayUrl.origin + (namespace ? `/${namespace}` : '');
127
+ const socket = io.connect(uri, {
128
+ path: gatewayUrl.pathname,
129
+ transports: ['websocket'],
130
+ reconnection: true,
131
+ query,
132
+ });
133
+ socket.on('connect_error', (err) => {
134
+ console.log(`connect_error due to ${err.message}`);
135
+ });
136
+ socket.on('csrf', () => {
137
+ // If CSRF is enabled, we will receive a CSRF event from the server and should send a CSRF event back to initiate the CSRF check
138
+ socket.emit('csrf', getCsrfResponseData());
139
+ });
140
+ socket.on('listen', () => {
141
+ // Send the register event only when the server is ready to listen
142
+ socket.emit('register', {});
143
+ });
144
+ socket.on('register', () => {
145
+ socket.emit('{"eventName": "_registerEvent", "data": "pivot2"}');
146
+ // socket.registeredInSisense = true;
147
+ });
148
+ socket.on('error', (err) => {
149
+ // eslint-disable-next-line no-console
150
+ console.warn(`"SisenseSocket" socket error "${err}"`);
151
+ });
152
+ return socket;
153
+ }
154
+ }
155
+ export default SisenseSocket;
@@ -0,0 +1,61 @@
1
+ /// <reference types="node" resolution-mode="require"/>
2
+ import EventEmitter from 'events';
3
+ import { SocketI } from '../types.js';
4
+ export declare class TestSocket implements SocketI {
5
+ /** @private */
6
+ events: EventEmitter;
7
+ /** @private */
8
+ ready: boolean;
9
+ /** @private */
10
+ onMessageCallback?: (type: string, data: any) => void;
11
+ constructor();
12
+ /**
13
+ * Checks if socket is ready for sending messages or not
14
+ *
15
+ * @returns {boolean} - true - ready
16
+ */
17
+ isReady(): boolean;
18
+ /**
19
+ * Attach event handler
20
+ *
21
+ * @param {string} event - event name
22
+ * @param {Function} cb - handler function
23
+ * @returns {void}
24
+ */
25
+ on(event: string, cb: (...args: Array<any>) => void): void;
26
+ /**
27
+ * Detach event handler
28
+ *
29
+ * @param {string} event - event name
30
+ * @param {Function} cb - handler function
31
+ * @returns {void}
32
+ */
33
+ off(event: string, cb: (...args: Array<any>) => void): void;
34
+ /**
35
+ * Send message via socket
36
+ *
37
+ * @param {string} event - message name
38
+ * @param {Array<any>} args - arguments
39
+ * @param {Array<any>} args.0 - message data
40
+ * @returns {void}
41
+ */
42
+ send(event: string, ...args: any[]): void;
43
+ /**
44
+ * Specific message handler
45
+ *
46
+ * @param {string} type - message type
47
+ * @param {string} subType - message subtype (query ID)
48
+ * @param {Function} callback - handler function
49
+ * @returns {Function} - unsubscribe function
50
+ */
51
+ onMessage(type: string, subType: string, callback: (type: string, data: any) => void): () => void;
52
+ /**
53
+ * Emulate receiving message from socket
54
+ *
55
+ * @param {string} event - message type
56
+ * @param {any} data - message data
57
+ * @returns {Promise} - waiting promise
58
+ */
59
+ trigger(event: string, data: any): any;
60
+ }
61
+ export default TestSocket;
@@ -0,0 +1,83 @@
1
+ import EventEmitter from 'events';
2
+ export class TestSocket {
3
+ constructor() {
4
+ /** @private */
5
+ this.ready = true;
6
+ this.events = new EventEmitter();
7
+ this.ready = true;
8
+ }
9
+ /**
10
+ * Checks if socket is ready for sending messages or not
11
+ *
12
+ * @returns {boolean} - true - ready
13
+ */
14
+ isReady() {
15
+ return this.ready;
16
+ }
17
+ /**
18
+ * Attach event handler
19
+ *
20
+ * @param {string} event - event name
21
+ * @param {Function} cb - handler function
22
+ * @returns {void}
23
+ */
24
+ on(event, cb) {
25
+ this.events.on(event, cb);
26
+ }
27
+ /**
28
+ * Detach event handler
29
+ *
30
+ * @param {string} event - event name
31
+ * @param {Function} cb - handler function
32
+ * @returns {void}
33
+ */
34
+ off(event, cb) {
35
+ this.events.removeListener(event, cb);
36
+ }
37
+ /**
38
+ * Send message via socket
39
+ *
40
+ * @param {string} event - message name
41
+ * @param {Array<any>} args - arguments
42
+ * @param {Array<any>} args.0 - message data
43
+ * @returns {void}
44
+ */
45
+ send(event, ...args) {
46
+ const noUsed = event || args;
47
+ this.ready = !!noUsed || true;
48
+ }
49
+ /**
50
+ * Specific message handler
51
+ *
52
+ * @param {string} type - message type
53
+ * @param {string} subType - message subtype (query ID)
54
+ * @param {Function} callback - handler function
55
+ * @returns {Function} - unsubscribe function
56
+ */
57
+ onMessage(type, subType, callback) {
58
+ this.onMessageCallback = callback;
59
+ const handler = () => { };
60
+ this.on('message', handler);
61
+ return () => {
62
+ this.off('message', handler);
63
+ };
64
+ }
65
+ /**
66
+ * Emulate receiving message from socket
67
+ *
68
+ * @param {string} event - message type
69
+ * @param {any} data - message data
70
+ * @returns {Promise} - waiting promise
71
+ */
72
+ trigger(event, data) {
73
+ return new Promise((resolve) => {
74
+ setTimeout(() => {
75
+ if (this.onMessageCallback) {
76
+ this.onMessageCallback(event, data);
77
+ }
78
+ resolve();
79
+ }, 10);
80
+ });
81
+ }
82
+ }
83
+ export default TestSocket;
@@ -0,0 +1,4 @@
1
+ /**
2
+ * Prepare data for CSRF response
3
+ */
4
+ export declare function getCsrfResponseData(): {};
@@ -0,0 +1,23 @@
1
+ /**
2
+ * Get XSRF token from `document.cookie`
3
+ */
4
+ function getCsrfToken(cookie = document.cookie) {
5
+ const csrfCookieName = 'XSRF-TOKEN';
6
+ const match = cookie.match(new RegExp(`(^| )${csrfCookieName}=([^;]+)`));
7
+ if (match !== null && match[2]) {
8
+ return match[2];
9
+ }
10
+ return null;
11
+ }
12
+ /**
13
+ * Prepare data for CSRF response
14
+ */
15
+ export function getCsrfResponseData() {
16
+ const csrfToken = getCsrfToken();
17
+ const data = {};
18
+ // The CSRF token is optional, but the domain needs to be added to the whitelist to pass the check without a token
19
+ if (csrfToken) {
20
+ data['X-XSRF-TOKEN'] = csrfToken;
21
+ }
22
+ return data;
23
+ }