http-request-manager 18.7.20 → 18.7.21

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 (197) hide show
  1. package/ARCHITECTURE.md +483 -0
  2. package/DATABASE_README.md +1176 -0
  3. package/HTTP_MANAGER_README.md +579 -0
  4. package/HTTP_SINGNALS_MANAGER_README.md +654 -0
  5. package/HTTP_STATE_MANAGER_README.md +948 -0
  6. package/INTERCEPTOR_README.md +549 -0
  7. package/LOCAL_STORAGE_README.md +1056 -0
  8. package/STORE_STATE_MANAGER_README.md +1322 -0
  9. package/UTILS_README.md +1186 -0
  10. package/WS_MANAGER_README.md +613 -0
  11. package/ng-package.json +8 -0
  12. package/package.json +1 -12
  13. package/src/lib/http-request-manager.module.ts +132 -0
  14. package/src/lib/http-request-services-demo/database-data-demo/database-data-demo.component.html +65 -0
  15. package/src/lib/http-request-services-demo/database-data-demo/database-data-demo.component.scss +0 -0
  16. package/src/lib/http-request-services-demo/database-data-demo/database-data-demo.component.ts +224 -0
  17. package/src/lib/http-request-services-demo/http-request-services-demo.component.html +114 -0
  18. package/src/lib/http-request-services-demo/http-request-services-demo.component.scss +6 -0
  19. package/src/lib/http-request-services-demo/http-request-services-demo.component.ts +52 -0
  20. package/src/lib/http-request-services-demo/local-storage-demo/local-storage-demo.component.html +195 -0
  21. package/src/lib/http-request-services-demo/local-storage-demo/local-storage-demo.component.scss +17 -0
  22. package/src/lib/http-request-services-demo/local-storage-demo/local-storage-demo.component.ts +206 -0
  23. package/src/lib/http-request-services-demo/local-storage-signals-demo/local-storage-signals-demo.component.html +200 -0
  24. package/src/lib/http-request-services-demo/local-storage-signals-demo/local-storage-signals-demo.component.scss +17 -0
  25. package/src/lib/http-request-services-demo/local-storage-signals-demo/local-storage-signals-demo.component.ts +212 -0
  26. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/download-file/download-file.component.html +53 -0
  27. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/download-file/download-file.component.scss +60 -0
  28. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/download-file/download-file.component.ts +72 -0
  29. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/file-download.module.ts +28 -0
  30. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/file-downloader.component.html +10 -0
  31. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/file-downloader.component.scss +29 -0
  32. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/file-downloader.component.ts +100 -0
  33. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/models/download-labels-model.ts +22 -0
  34. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/spinner/spinner.component.html +8 -0
  35. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/spinner/spinner.component.scss +19 -0
  36. package/src/lib/http-request-services-demo/request-manager-demo/file-downloader/spinner/spinner.component.ts +26 -0
  37. package/src/lib/http-request-services-demo/request-manager-demo/models/app-session.model.ts +30 -0
  38. package/src/lib/http-request-services-demo/request-manager-demo/models/app.model.ts +19 -0
  39. package/src/lib/http-request-services-demo/request-manager-demo/models/get-sample.model.ts +25 -0
  40. package/src/lib/http-request-services-demo/request-manager-demo/models/sample-ai-prompt.ts +19 -0
  41. package/src/lib/http-request-services-demo/request-manager-demo/models/sample-client-details.ts +24 -0
  42. package/src/lib/http-request-services-demo/request-manager-demo/models/sample-client-info.ts +30 -0
  43. package/src/lib/http-request-services-demo/request-manager-demo/models/sample-client.model.ts +49 -0
  44. package/src/lib/http-request-services-demo/request-manager-demo/models/sample-mapper-client-info.ts +33 -0
  45. package/src/lib/http-request-services-demo/request-manager-demo/request-manager-demo.component.html +392 -0
  46. package/src/lib/http-request-services-demo/request-manager-demo/request-manager-demo.component.scss +24 -0
  47. package/src/lib/http-request-services-demo/request-manager-demo/request-manager-demo.component.ts +461 -0
  48. package/src/lib/http-request-services-demo/request-manager-state-demo/request-manager-state-demo.component.html +393 -0
  49. package/src/lib/http-request-services-demo/request-manager-state-demo/request-manager-state-demo.component.scss +24 -0
  50. package/src/lib/http-request-services-demo/request-manager-state-demo/request-manager-state-demo.component.ts +421 -0
  51. package/src/lib/http-request-services-demo/request-manager-state-demo/services/state-manager-demo.service.ts +87 -0
  52. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/services/state-data-request.service.ts +120 -0
  53. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-ai-messaging/ws-ai-messaging.component.css +0 -0
  54. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-ai-messaging/ws-ai-messaging.component.html +3 -0
  55. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-ai-messaging/ws-ai-messaging.component.ts +16 -0
  56. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-chats/ws-chats.component.css +0 -0
  57. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-chats/ws-chats.component.html +3 -0
  58. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-chats/ws-chats.component.ts +16 -0
  59. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-data-control/ws-data-control.component.css +31 -0
  60. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-data-control/ws-data-control.component.html +72 -0
  61. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-data-control/ws-data-control.component.scss +41 -0
  62. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-data-control/ws-data-control.component.spec.ts +205 -0
  63. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-data-control/ws-data-control.component.ts +77 -0
  64. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-messaging/ws-messaging.component.css +11 -0
  65. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-messaging/ws-messaging.component.html +96 -0
  66. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-messaging/ws-messaging.component.spec.ts +31 -0
  67. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-messaging/ws-messaging.component.ts +229 -0
  68. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-notifications/ws-notifications.component.css +30 -0
  69. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-notifications/ws-notifications.component.html +172 -0
  70. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-notifications/ws-notifications.component.spec.ts +31 -0
  71. package/src/lib/http-request-services-demo/request-manager-ws-demo/components/ws-notifications/ws-notifications.component.ts +239 -0
  72. package/src/lib/http-request-services-demo/request-manager-ws-demo/models/oidc-client.model.ts +31 -0
  73. package/src/lib/http-request-services-demo/request-manager-ws-demo/models/user-data.model.ts +32 -0
  74. package/src/lib/http-request-services-demo/request-manager-ws-demo/request-manager-ws-demo.component.css +0 -0
  75. package/src/lib/http-request-services-demo/request-manager-ws-demo/request-manager-ws-demo.component.html +84 -0
  76. package/src/lib/http-request-services-demo/request-manager-ws-demo/request-manager-ws-demo.component.ts +41 -0
  77. package/src/lib/http-request-services-demo/request-manager-ws-demo/services/index.ts +3 -0
  78. package/src/lib/http-request-services-demo/request-manager-ws-demo/services/message-service-demo.service.ts +83 -0
  79. package/src/lib/http-request-services-demo/request-manager-ws-demo/services/notification-service-demo.service.ts +147 -0
  80. package/src/lib/http-request-services-demo/request-manager-ws-demo/services/state-service-demo.service.ts +158 -0
  81. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/download-file/download-file.component.html +53 -0
  82. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/download-file/download-file.component.scss +60 -0
  83. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/download-file/download-file.component.ts +72 -0
  84. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/file-download.module.ts +28 -0
  85. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/file-downloader.component.html +10 -0
  86. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/file-downloader.component.scss +29 -0
  87. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/file-downloader.component.ts +100 -0
  88. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/models/download-labels-model.ts +22 -0
  89. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/spinner/spinner.component.html +8 -0
  90. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/spinner/spinner.component.scss +19 -0
  91. package/src/lib/http-request-services-demo/request-signals-manager-demo/file-downloader/spinner/spinner.component.ts +26 -0
  92. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/app-session.model.ts +30 -0
  93. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/app.model.ts +19 -0
  94. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/get-sample.model.ts +25 -0
  95. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/sample-ai-prompt.ts +19 -0
  96. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/sample-client-details.ts +24 -0
  97. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/sample-client-info.ts +30 -0
  98. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/sample-client.model.ts +49 -0
  99. package/src/lib/http-request-services-demo/request-signals-manager-demo/models/sample-mapper-client-info.ts +33 -0
  100. package/src/lib/http-request-services-demo/request-signals-manager-demo/request-signals-manager-demo.component.html +380 -0
  101. package/src/lib/http-request-services-demo/request-signals-manager-demo/request-signals-manager-demo.component.scss +24 -0
  102. package/src/lib/http-request-services-demo/request-signals-manager-demo/request-signals-manager-demo.component.ts +410 -0
  103. package/src/lib/http-request-services-demo/store-state-manager-demo/models/settings.model.ts +28 -0
  104. package/src/lib/http-request-services-demo/store-state-manager-demo/services/settings-state.service.ts +48 -0
  105. package/src/lib/http-request-services-demo/store-state-manager-demo/store-state-manager-demo.component.css +0 -0
  106. package/src/lib/http-request-services-demo/store-state-manager-demo/store-state-manager-demo.component.html +23 -0
  107. package/src/lib/http-request-services-demo/store-state-manager-demo/store-state-manager-demo.component.ts +36 -0
  108. package/src/lib/index.ts +3 -0
  109. package/src/lib/interceptors/credentials.interceptor.ts +16 -0
  110. package/src/lib/interceptors/index.ts +6 -0
  111. package/src/lib/interceptors/models/error-settings.model.ts +22 -0
  112. package/src/lib/interceptors/models/index.ts +2 -0
  113. package/src/lib/interceptors/proxy-debugger.interceptor.ts +46 -0
  114. package/src/lib/interceptors/request-error.interceptor.ts +65 -0
  115. package/src/lib/interceptors/request-header.interceptor.ts +53 -0
  116. package/src/lib/models/config-http-options.model.ts +42 -0
  117. package/src/lib/models/config-local-storage-options.model.ts +27 -0
  118. package/src/lib/models/config-options.model.ts +27 -0
  119. package/src/lib/models/config-token.model.ts +9 -0
  120. package/src/lib/models/data-type.enum.ts +5 -0
  121. package/src/lib/models/database-storage.model.ts +24 -0
  122. package/src/lib/models/index.ts +12 -0
  123. package/src/lib/models/retry-options.model.ts +22 -0
  124. package/src/lib/services/database-manager-service/database.manager.service.ts +262 -0
  125. package/src/lib/services/database-manager-service/db.storage.service.ts +207 -0
  126. package/src/lib/services/database-manager-service/index.ts +4 -0
  127. package/src/lib/services/database-manager-service/models/index.ts +2 -0
  128. package/src/lib/services/database-manager-service/models/table-schema.ts +33 -0
  129. package/src/lib/services/index.ts +12 -0
  130. package/src/lib/services/local-storage-manager-service/index.ts +4 -0
  131. package/src/lib/services/local-storage-manager-service/local-storage-manager.service.spec.ts +71 -0
  132. package/src/lib/services/local-storage-manager-service/local-storage-manager.service.ts +426 -0
  133. package/src/lib/services/local-storage-manager-service/local-storage-signals-manager.service.spec.ts +67 -0
  134. package/src/lib/services/local-storage-manager-service/local-storage-signals-manager.service.ts +345 -0
  135. package/src/lib/services/local-storage-manager-service/models/global-store-options.model.ts +30 -0
  136. package/src/lib/services/local-storage-manager-service/models/index.ts +6 -0
  137. package/src/lib/services/local-storage-manager-service/models/setting-options.model.ts +35 -0
  138. package/src/lib/services/local-storage-manager-service/models/storage-data.model.ts +24 -0
  139. package/src/lib/services/local-storage-manager-service/models/storage-option.model.ts +32 -0
  140. package/src/lib/services/local-storage-manager-service/models/storage-type.enum.ts +5 -0
  141. package/src/lib/services/request-manager-services/README.md +268 -0
  142. package/src/lib/services/request-manager-services/http-manager-signals.service.ts +246 -0
  143. package/src/lib/services/request-manager-services/http-manager.service.spec.ts +232 -0
  144. package/src/lib/services/request-manager-services/http-manager.service.ts +274 -0
  145. package/src/lib/services/request-manager-services/index.ts +8 -0
  146. package/src/lib/services/request-manager-services/request-signals.service.ts +214 -0
  147. package/src/lib/services/request-manager-services/request.service.ts +309 -0
  148. package/src/lib/services/request-manager-services/rxjs-operators/countdown.ts +17 -0
  149. package/src/lib/services/request-manager-services/rxjs-operators/delay-retry.ts +16 -0
  150. package/src/lib/services/request-manager-services/rxjs-operators/index.ts +4 -0
  151. package/src/lib/services/request-manager-services/rxjs-operators/request-polling.ts +35 -0
  152. package/src/lib/services/request-manager-services/rxjs-operators/request-streaming.ts +436 -0
  153. package/src/lib/services/request-manager-state-service/http-manager-state.store.ts +1321 -0
  154. package/src/lib/services/request-manager-state-service/index.ts +3 -0
  155. package/src/lib/services/request-manager-state-service/models/api-request.model.ts +61 -0
  156. package/src/lib/services/request-manager-state-service/models/index.ts +6 -0
  157. package/src/lib/services/request-manager-state-service/models/request-options.model.ts +22 -0
  158. package/src/lib/services/request-manager-state-service/models/stream-type.enum.ts +13 -0
  159. package/src/lib/services/request-manager-state-service/models/ws-options.model.ts +39 -0
  160. package/src/lib/services/store-state-manager-service/index.ts +3 -0
  161. package/src/lib/services/store-state-manager-service/models/index.ts +2 -0
  162. package/src/lib/services/store-state-manager-service/models/state-storage-options.model.ts +24 -0
  163. package/src/lib/services/store-state-manager-service/store-state-manager.service.ts +88 -0
  164. package/src/lib/services/utils/app.service.spec.ts +25 -0
  165. package/src/lib/services/utils/app.service.ts +21 -0
  166. package/src/lib/services/utils/encryption/README.md +79 -0
  167. package/src/lib/services/utils/encryption/asymmetrical-encryption.service.ts +282 -0
  168. package/src/lib/services/utils/encryption/encryption-test.service.ts +39 -0
  169. package/src/lib/services/utils/encryption/index.ts +5 -0
  170. package/src/lib/services/utils/encryption/random.ts +81 -0
  171. package/src/lib/services/utils/encryption/symmetrical-encryption.service.ts +93 -0
  172. package/src/lib/services/utils/headers.service.spec.ts +80 -0
  173. package/src/lib/services/utils/headers.service.ts +18 -0
  174. package/src/lib/services/utils/index.ts +7 -0
  175. package/src/lib/services/utils/object-merger.service.spec.ts +18 -0
  176. package/src/lib/services/utils/object-merger.service.ts +78 -0
  177. package/src/lib/services/utils/path-query.service.spec.ts +117 -0
  178. package/src/lib/services/utils/path-query.service.ts +69 -0
  179. package/src/lib/services/utils/random-color.utils.ts +83 -0
  180. package/src/lib/services/utils/utils.service.spec.ts +165 -0
  181. package/src/lib/services/utils/utils.service.ts +192 -0
  182. package/src/lib/services/ws-manager-service/index.ts +4 -0
  183. package/src/lib/services/ws-manager-service/models/channel-info.model.ts +24 -0
  184. package/src/lib/services/ws-manager-service/models/channel-message-data.model.ts +24 -0
  185. package/src/lib/services/ws-manager-service/models/channel-message.model.ts +24 -0
  186. package/src/lib/services/ws-manager-service/models/communication-type.enum.ts +5 -0
  187. package/src/lib/services/ws-manager-service/models/index.ts +5 -0
  188. package/src/lib/services/ws-manager-service/models/ws-user.model.ts +38 -0
  189. package/src/lib/services/ws-manager-service/services/index.ts +3 -0
  190. package/src/lib/services/ws-manager-service/services/websocket.service.ts +392 -0
  191. package/src/public-api.ts +14 -0
  192. package/tsconfig.lib.json +32 -0
  193. package/tsconfig.lib.prod.json +10 -0
  194. package/tsconfig.spec.json +14 -0
  195. package/fesm2022/http-request-manager.mjs +0 -7633
  196. package/fesm2022/http-request-manager.mjs.map +0 -1
  197. package/types/http-request-manager.d.ts +0 -2277
@@ -0,0 +1,392 @@
1
+ import { Injectable } from '@angular/core';
2
+ import { BehaviorSubject, Observable } from 'rxjs';
3
+ import { WSOptions } from '../../request-manager-state-service';
4
+ import { UUID_STR } from '../../utils/encryption/random';
5
+
6
+ @Injectable({
7
+ providedIn: 'root',
8
+ })
9
+ export class WebsocketService {
10
+
11
+ private socket: WebSocket | null = null;
12
+
13
+ private messages = new BehaviorSubject<any>(null);
14
+ public messages$: Observable<any> = this.messages.asObservable();
15
+
16
+ private connectionStatus = new BehaviorSubject<boolean>(false);
17
+ public connectionStatus$: Observable<boolean> = this.connectionStatus.asObservable();
18
+
19
+ private isSubscribed: boolean = false;
20
+
21
+ // Track currently subscribed channels
22
+ private subscribedChannels = new BehaviorSubject<Set<string>>(new Set());
23
+ public subscribedChannels$: Observable<Set<string>> = this.subscribedChannels.asObservable();
24
+
25
+ // Store last options for reconnection
26
+ private lastOptions: WSOptions | null = null;
27
+
28
+ private getSessionId(): string {
29
+ return sessionStorage.getItem('WSID') ?? (() => {
30
+ const uuid = UUID_STR()
31
+ sessionStorage.setItem('WSID', uuid)
32
+ return uuid
33
+ })()
34
+ }
35
+
36
+ private sendSubscribe(channelName: string, user: any) {
37
+
38
+ // Check if already subscribed to THIS specific channel (not just any channel)
39
+ const alreadySubscribed = this.subscribedChannels.value.has(channelName);
40
+
41
+ if (this.socket?.readyState === WebSocket.OPEN && !alreadySubscribed) {
42
+ const message = {
43
+ type: 'subscribe',
44
+ subscribedChannel: channelName,
45
+ content: {
46
+ id: this.getSessionId(),
47
+ ...user
48
+ }
49
+ };
50
+ this.socket.send(JSON.stringify(message));
51
+
52
+ // Track this channel as subscribed
53
+ const current = new Set(this.subscribedChannels.value);
54
+ current.add(channelName);
55
+ this.subscribedChannels.next(current);
56
+
57
+ this.isSubscribed = true; // Keep for backward compatibility
58
+ console.log(`[CLIENT] Sent initial subscription to: ${channelName}`);
59
+ } else {
60
+ console.warn(`[CLIENT] Subscription prevented. Open: ${this.socket?.readyState === WebSocket.OPEN}, Already subscribed to ${channelName}: ${alreadySubscribed}`);
61
+ }
62
+ }
63
+
64
+ connect(options: WSOptions, jwtToken: string) {
65
+
66
+ if (this.socket) {
67
+
68
+ if (this.socket.readyState === WebSocket.OPEN) {
69
+ console.log('WebSocket connection is already OPEN.');
70
+ return;
71
+ }
72
+
73
+ if (this.socket.readyState === WebSocket.CONNECTING) {
74
+ console.log('WebSocket is already CONNECTING. Waiting for handshake.');
75
+ return;
76
+ }
77
+
78
+ if (this.socket.readyState === WebSocket.CLOSING || this.socket.readyState === WebSocket.CLOSED) {
79
+ console.log(`Cleaning up stale socket (State: ${this.socket.readyState}).`);
80
+ this.socket.close();
81
+ this.socket = null;
82
+ }
83
+ }
84
+
85
+ this.isSubscribed = false;
86
+ // Clear tracked subscriptions for new connection
87
+ this.subscribedChannels.next(new Set());
88
+
89
+ const sessionId = this.getSessionId();
90
+ const URL = (jwtToken) ? `${options.wsServer}?token=${jwtToken}&sessionId=${sessionId}` : `${options.wsServer}?sessionId=${sessionId}`;
91
+
92
+ this.socket = new WebSocket(URL);
93
+
94
+ this.socket.onopen = () => {
95
+ console.log(`📡 Connected to WebSocket`);
96
+ this.connectionStatus.next(true);
97
+ this.lastOptions = options;
98
+
99
+ // Subscribe to primary channel
100
+ this.sendSubscribe(options.id, options.user);
101
+
102
+ // Auto-subscribe to additional channels from options.channels[]
103
+ if (options.channels && options.channels.length > 0) {
104
+ options.channels.forEach(channel => {
105
+ if (channel !== options.id) {
106
+ this.subscribeToChannel(channel);
107
+ }
108
+ });
109
+ }
110
+
111
+ // Re-subscribe to any previously subscribed channels (reconnection scenario)
112
+ const previousChannels = this.subscribedChannels.value;
113
+ if (previousChannels.size > 0) {
114
+ previousChannels.forEach(channel => {
115
+ if (channel !== options.id && (!options.channels || !options.channels.includes(channel))) {
116
+ this.subscribeToChannel(channel);
117
+ }
118
+ });
119
+ }
120
+ };
121
+
122
+ this.socket.onmessage = (event) => {
123
+
124
+ try {
125
+
126
+ const data = JSON.parse(event.data);
127
+
128
+ if (data.error && data.error === 'JWT_INVALID') {
129
+
130
+ console.error('JWT validation failed. Authentication error!');
131
+
132
+ this.messages.next(data);
133
+ this.connectionStatus.next(false);
134
+ this.socket?.close();
135
+
136
+ return;
137
+
138
+ }
139
+
140
+ this.messages.next(data);
141
+
142
+ } catch (error) {
143
+ console.error('Error parsing WebSocket message:', event.data);
144
+ }
145
+
146
+ };
147
+
148
+ this.socket.onclose = () => {
149
+
150
+ console.log('WebSocket connection closed');
151
+
152
+ this.connectionStatus.next(false);
153
+ this.socket = null;
154
+ };
155
+
156
+ this.socket.onerror = (error) => {
157
+ console.error('WebSocket error:', error);
158
+ this.connectionStatus.next(false);
159
+ };
160
+
161
+ }
162
+
163
+ disconnect() {
164
+ if (this.socket) {
165
+ this.socket.close();
166
+ this.socket = null;
167
+ }
168
+ }
169
+
170
+ subscribeToChannel(channelName: string) {
171
+
172
+ if (this.socket?.readyState === WebSocket.OPEN) {
173
+
174
+ const message = {
175
+ type: 'subscribe',
176
+ subscribedChannel: channelName,
177
+ content: {}
178
+ };
179
+
180
+ this.socket.send(JSON.stringify(message));
181
+
182
+ // Track locally - create new Set to trigger change detection
183
+ const current = new Set(this.subscribedChannels.value);
184
+ current.add(channelName);
185
+ this.subscribedChannels.next(current);
186
+ console.log(`📝 Subscribed to channel: ${channelName}`);
187
+
188
+ } else {
189
+ console.warn('Cannot subscribe: WebSocket not yet open.');
190
+ }
191
+
192
+ }
193
+
194
+ subscribeToChannels(channelNames: string[]) {
195
+ if (this.socket?.readyState === WebSocket.OPEN) {
196
+ channelNames.forEach(channel => this.subscribeToChannel(channel));
197
+ } else {
198
+ console.warn('Cannot subscribe: WebSocket not yet open.');
199
+ }
200
+ }
201
+
202
+ unsubscribeFromChannel(channel: string) {
203
+ if (this.socket?.readyState === WebSocket.OPEN) {
204
+ this.socket.send(JSON.stringify({ type: 'unsubscribe', subscribedChannel: channel }));
205
+
206
+ // Remove from local tracking - create new Set to trigger change detection
207
+ const current = new Set(this.subscribedChannels.value);
208
+ current.delete(channel);
209
+ this.subscribedChannels.next(current);
210
+ console.log(`💬 Unsubscribed from channel: ${channel}`);
211
+ } else {
212
+ console.error('WebSocket is not open. Cannot unsubscribe from channel.');
213
+ }
214
+ }
215
+
216
+ unsubscribeToChannel(channel: string) {
217
+ // Deprecated: Use unsubscribeFromChannel instead
218
+ this.unsubscribeFromChannel(channel);
219
+ }
220
+
221
+ getSubscribedChannels(): Set<string> {
222
+ return this.subscribedChannels.value;
223
+ }
224
+
225
+ sendBroadcast(content: any) {
226
+ if (this.socket?.readyState === WebSocket.OPEN) {
227
+ this.socket.send(JSON.stringify({ type: 'broadcast', content }));
228
+ console.log(`📢 Send broadcast: ${content}`);
229
+ } else {
230
+ console.error('WebSocket is not open. Cannot send broadcast.');
231
+ }
232
+ }
233
+
234
+ sendMessageInChannel(channel: string, content: any) {
235
+ if (this.socket?.readyState === WebSocket.OPEN) {
236
+ this.socket.send(JSON.stringify({ type: 'stateMangerMessage', subscribedChannel: channel, content }));
237
+ console.log(`💬 Send message:`, content);
238
+ } else {
239
+ console.error('WebSocket is not open. Cannot send message.');
240
+ }
241
+ }
242
+
243
+ /**
244
+ * Send a message to a specific channel for channel-based messaging
245
+ * This uses the 'message' type which broadcasts to all subscribers in the channel
246
+ */
247
+ sendChannelMessage(channel: string, content: any) {
248
+ if (this.socket?.readyState === WebSocket.OPEN) {
249
+ this.socket.send(JSON.stringify({ type: 'message', subscribedChannel: channel, content }));
250
+ console.log(`💬 Send channel message to [${channel}]:`, content);
251
+ } else {
252
+ console.error('WebSocket is not open. Cannot send channel message.');
253
+ }
254
+ }
255
+
256
+ sendMessageToUser(user: string, content: any) {
257
+ if (this.socket?.readyState === WebSocket.OPEN) {
258
+ this.socket.send(JSON.stringify({ type: 'userMessage', subscribedChannel: user, content }));
259
+ console.log(`💬 Send message:`, content);
260
+ } else {
261
+ console.error('WebSocket is not open. Cannot send message.');
262
+ }
263
+ }
264
+
265
+ getAllChannels() {
266
+ if (this.socket?.readyState === WebSocket.OPEN) {
267
+ this.socket.send(JSON.stringify({ type: 'getChannels' }));
268
+ console.log('🗂️ List of all channels');
269
+ } else {
270
+ console.error('WebSocket is not open. Cannot request channels.');
271
+ }
272
+ }
273
+
274
+ createChannel(channel: string) {
275
+ if (this.socket?.readyState === WebSocket.OPEN) {
276
+ this.socket.send(JSON.stringify({ type: 'createChannel', content: channel }));
277
+ console.log('🗂️ Created channel:', channel);
278
+ } else {
279
+ console.error('WebSocket is not open. Cannot request channels.');
280
+ }
281
+ }
282
+
283
+ deleteChannel(channel: string) {
284
+ if (this.socket?.readyState === WebSocket.OPEN) {
285
+ this.socket.send(JSON.stringify({ type: 'deleteChannel', content: channel }));
286
+ console.log('🗂️ Delete channel:', channel);
287
+ } else {
288
+ console.error('WebSocket is not open. Cannot request channels.');
289
+ }
290
+ }
291
+
292
+ getUsersInChannel(channel: string) {
293
+ if (this.socket?.readyState === WebSocket.OPEN) {
294
+ this.socket.send(JSON.stringify({ type: 'getUsers', subscribedChannel: channel }));
295
+ console.log(`👥 List all users in channel: ${channel}`);
296
+ } else {
297
+ console.error('WebSocket is not open. Cannot request users.');
298
+ }
299
+ }
300
+
301
+ // =====================
302
+ // Notification Channel Methods (MES- prefix)
303
+ // =====================
304
+
305
+ /**
306
+ * Create a notification channel
307
+ */
308
+ createNotificationChannel(channel: string) {
309
+ if (this.socket?.readyState === WebSocket.OPEN) {
310
+ this.socket.send(JSON.stringify({ type: 'createNotificationChannel', content: channel }));
311
+ console.log('📢 Created notification channel:', channel);
312
+ } else {
313
+ console.error('WebSocket is not open. Cannot create notification channel.');
314
+ }
315
+ }
316
+
317
+ /**
318
+ * Get all notification channels (in-memory)
319
+ */
320
+ getNotificationChannels() {
321
+ if (this.socket?.readyState === WebSocket.OPEN) {
322
+ this.socket.send(JSON.stringify({ type: 'getNotificationChannels' }));
323
+ console.log('📢 Requested notification channels list');
324
+ } else {
325
+ console.error('WebSocket is not open. Cannot request notification channels.');
326
+ }
327
+ }
328
+
329
+ /**
330
+ * Get today's notification channels from database
331
+ * Returns unique channels that have notifications posted today
332
+ */
333
+ getTodaysNotificationChannels() {
334
+ if (this.socket?.readyState === WebSocket.OPEN) {
335
+ this.socket.send(JSON.stringify({ type: 'getTodaysNotificationChannels' }));
336
+ console.log('📢 Requested today\'s notification channels from DB');
337
+ } else {
338
+ console.error('WebSocket is not open. Cannot request today\'s notification channels.');
339
+ }
340
+ }
341
+
342
+ /**
343
+ * Subscribe to a notification channel with optional date filters
344
+ */
345
+ subscribeToNotificationChannel(channel: string, options?: { startEpoch?: number; endEpoch?: number }, user?: any) {
346
+ if (this.socket?.readyState === WebSocket.OPEN) {
347
+ this.socket.send(JSON.stringify({
348
+ type: 'subscribeNotifications',
349
+ subscribedChannel: channel,
350
+ content: {
351
+ ...options,
352
+ ...user
353
+ }
354
+ }));
355
+ console.log(`📢 Subscribed to notification channel: ${channel}`, options);
356
+ } else {
357
+ console.error('WebSocket is not open. Cannot subscribe to notification channel.');
358
+ }
359
+ }
360
+
361
+ /**
362
+ * Unsubscribe from a notification channel
363
+ */
364
+ unsubscribeFromNotificationChannel(channel: string) {
365
+ if (this.socket?.readyState === WebSocket.OPEN) {
366
+ this.socket.send(JSON.stringify({
367
+ type: 'unsubscribeNotifications',
368
+ subscribedChannel: channel
369
+ }));
370
+ console.log(`📢 Unsubscribed from notification channel: ${channel}`);
371
+ } else {
372
+ console.error('WebSocket is not open. Cannot unsubscribe from notification channel.');
373
+ }
374
+ }
375
+
376
+ /**
377
+ * Send a notification to a channel
378
+ */
379
+ sendNotification(channel: string, content: any) {
380
+ if (this.socket?.readyState === WebSocket.OPEN) {
381
+ this.socket.send(JSON.stringify({
382
+ type: 'notification',
383
+ subscribedChannel: channel,
384
+ content
385
+ }));
386
+ console.log(`📢 Sent notification to channel: ${channel}`, content);
387
+ } else {
388
+ console.error('WebSocket is not open. Cannot send notification.');
389
+ }
390
+ }
391
+
392
+ }
@@ -0,0 +1,14 @@
1
+ /*
2
+ * Public API Surface of http-request-manager
3
+ */
4
+
5
+ export * from './lib/index';
6
+ export * from './lib/http-request-manager.module';
7
+
8
+ export * from './lib/http-request-services-demo/http-request-services-demo.component';
9
+
10
+ export * from './lib/http-request-services-demo/database-data-demo/database-data-demo.component';
11
+ export * from './lib/http-request-services-demo/local-storage-demo/local-storage-demo.component';
12
+ export * from './lib/http-request-services-demo/request-manager-demo/request-manager-demo.component';
13
+ export * from './lib/http-request-services-demo/request-manager-state-demo/request-manager-state-demo.component';
14
+
@@ -0,0 +1,32 @@
1
+ /* To learn more about this file see: https://angular.io/config/tsconfig. */
2
+ {
3
+ "extends": "../../tsconfig.json",
4
+ "compilerOptions": {
5
+ "outDir": "../../dist/http-request-manager",
6
+ "declaration": true,
7
+ "declarationMap": true,
8
+ "inlineSources": true,
9
+ "types": [],
10
+ "baseUrl": "./",
11
+ "paths": {
12
+ "@angular/*": ["node_modules/@angular/*"],
13
+ "http-request-manager": ["node_modules/http-request-manager"],
14
+ },
15
+ "target": "ES2022",
16
+ "lib": [
17
+ "dom",
18
+ "ES2022"
19
+ ]
20
+ },
21
+ "angularCompilerOptions": {
22
+ "skipTemplateCodegen": true,
23
+ "strictMetadataEmit": true,
24
+ "enableResourceInlining": true,
25
+ "strictInjectionParameters": true,
26
+ "strictTemplates": true
27
+ },
28
+ "exclude": [
29
+ "src/test.ts",
30
+ "**/*.spec.ts"
31
+ ]
32
+ }
@@ -0,0 +1,10 @@
1
+ /* To learn more about this file see: https://angular.io/config/tsconfig. */
2
+ {
3
+ "extends": "./tsconfig.lib.json",
4
+ "compilerOptions": {
5
+ "declarationMap": false
6
+ },
7
+ "angularCompilerOptions": {
8
+ "compilationMode": "partial"
9
+ }
10
+ }
@@ -0,0 +1,14 @@
1
+ /* To learn more about this file see: https://angular.io/config/tsconfig. */
2
+ {
3
+ "extends": "../../tsconfig.json",
4
+ "compilerOptions": {
5
+ "outDir": "../../out-tsc/spec",
6
+ "types": [
7
+ "jasmine"
8
+ ]
9
+ },
10
+ "include": [
11
+ "**/*.spec.ts",
12
+ "**/*.d.ts"
13
+ ]
14
+ }