@involvex/youtube-music-cli 0.0.46 → 0.0.48

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 (118) hide show
  1. package/CHANGELOG.md +4 -0
  2. package/dist/cli.js.map +1004 -0
  3. package/dist/source/hooks/usePlayer.d.ts +1 -0
  4. package/dist/source/services/player-state/player-state.service.d.ts +1 -0
  5. package/dist/source/stores/player.store.d.ts +1 -0
  6. package/dist/source/types/actions.d.ts +4 -0
  7. package/dist/source/types/player.types.d.ts +3 -2
  8. package/dist/source/utils/constants.d.ts +1 -0
  9. package/dist/source/utils/icons.d.ts +1 -0
  10. package/dist/youtube-music-cli +0 -0
  11. package/package.json +1 -1
  12. package/dist/eslint.config.js +0 -55
  13. package/dist/package.json +0 -120
  14. package/dist/scripts/build-cli.js +0 -46
  15. package/dist/source/app.js +0 -17
  16. package/dist/source/cli.js +0 -504
  17. package/dist/source/components/common/ErrorBoundary.js +0 -22
  18. package/dist/source/components/common/Help.js +0 -18
  19. package/dist/source/components/common/ShortcutsBar.js +0 -80
  20. package/dist/source/components/config/ConfigLayout.js +0 -84
  21. package/dist/source/components/config/KeybindingsLayout.js +0 -107
  22. package/dist/source/components/export/ExportLayout.js +0 -111
  23. package/dist/source/components/import/ImportLayout.js +0 -119
  24. package/dist/source/components/import/ImportProgress.js +0 -73
  25. package/dist/source/components/layouts/ExploreLayout.js +0 -72
  26. package/dist/source/components/layouts/HistoryLayout.js +0 -37
  27. package/dist/source/components/layouts/LyricsLayout.js +0 -89
  28. package/dist/source/components/layouts/MainLayout.js +0 -190
  29. package/dist/source/components/layouts/MiniPlayerLayout.js +0 -20
  30. package/dist/source/components/layouts/PlayerLayout.js +0 -9
  31. package/dist/source/components/layouts/PluginsLayout.js +0 -77
  32. package/dist/source/components/layouts/SearchLayout.js +0 -193
  33. package/dist/source/components/layouts/TrendingLayout.js +0 -59
  34. package/dist/source/components/player/NowPlaying.js +0 -45
  35. package/dist/source/components/player/PlayerControls.js +0 -83
  36. package/dist/source/components/player/ProgressBar.js +0 -19
  37. package/dist/source/components/player/QueueList.js +0 -36
  38. package/dist/source/components/player/Suggestions.js +0 -50
  39. package/dist/source/components/playlist/PlaylistList.js +0 -138
  40. package/dist/source/components/plugins/PluginInstallDialog.js +0 -41
  41. package/dist/source/components/plugins/PluginsAvailable.js +0 -55
  42. package/dist/source/components/plugins/PluginsList.js +0 -18
  43. package/dist/source/components/search/SearchBar.js +0 -55
  44. package/dist/source/components/search/SearchHistory.js +0 -35
  45. package/dist/source/components/search/SearchResults.js +0 -280
  46. package/dist/source/components/settings/Settings.js +0 -211
  47. package/dist/source/components/theme/ThemeSwitcher.js +0 -11
  48. package/dist/source/config/themes.config.js +0 -123
  49. package/dist/source/contexts/theme.context.js +0 -29
  50. package/dist/source/hooks/useKeyboard.js +0 -188
  51. package/dist/source/hooks/useKeyboardBlocker.js +0 -45
  52. package/dist/source/hooks/useNavigation.js +0 -5
  53. package/dist/source/hooks/usePlayer.js +0 -43
  54. package/dist/source/hooks/usePlaylist.js +0 -65
  55. package/dist/source/hooks/useSearch.js +0 -76
  56. package/dist/source/hooks/useSleepTimer.js +0 -48
  57. package/dist/source/hooks/useTerminalSize.js +0 -24
  58. package/dist/source/hooks/useTheme.js +0 -5
  59. package/dist/source/hooks/useYouTubeMusic.js +0 -112
  60. package/dist/source/main.js +0 -127
  61. package/dist/source/services/cache/cache.service.js +0 -67
  62. package/dist/source/services/completions/completions.service.js +0 -313
  63. package/dist/source/services/config/config.service.js +0 -191
  64. package/dist/source/services/discord/discord-rpc.service.js +0 -95
  65. package/dist/source/services/download/download.service.js +0 -350
  66. package/dist/source/services/export/export.service.js +0 -131
  67. package/dist/source/services/history/history.service.js +0 -83
  68. package/dist/source/services/import/import.service.js +0 -272
  69. package/dist/source/services/import/spotify.service.js +0 -171
  70. package/dist/source/services/import/track-matcher.service.js +0 -271
  71. package/dist/source/services/import/youtube-import.service.js +0 -84
  72. package/dist/source/services/logger/logger.service.js +0 -52
  73. package/dist/source/services/lyrics/lyrics.service.js +0 -93
  74. package/dist/source/services/mpris/mpris.service.js +0 -78
  75. package/dist/source/services/notification/notification.service.js +0 -57
  76. package/dist/source/services/player/dependency-check.service.js +0 -140
  77. package/dist/source/services/player/player.service.js +0 -478
  78. package/dist/source/services/player-state/player-state.service.js +0 -122
  79. package/dist/source/services/plugin/plugin-audio-api.js +0 -36
  80. package/dist/source/services/plugin/plugin-context.js +0 -256
  81. package/dist/source/services/plugin/plugin-hooks.service.js +0 -135
  82. package/dist/source/services/plugin/plugin-installer.service.js +0 -248
  83. package/dist/source/services/plugin/plugin-loader.service.js +0 -161
  84. package/dist/source/services/plugin/plugin-permissions.service.js +0 -194
  85. package/dist/source/services/plugin/plugin-registry.service.js +0 -215
  86. package/dist/source/services/plugin/plugin-ui-api.js +0 -46
  87. package/dist/source/services/plugin/plugin-updater.service.js +0 -206
  88. package/dist/source/services/scrobbling/scrobbling.service.js +0 -115
  89. package/dist/source/services/sleep-timer/sleep-timer.service.js +0 -45
  90. package/dist/source/services/version-check/version-check.service.js +0 -121
  91. package/dist/source/services/web/static-file.service.js +0 -185
  92. package/dist/source/services/web/web-server-manager.js +0 -506
  93. package/dist/source/services/web/web-streaming.service.js +0 -290
  94. package/dist/source/services/web/websocket.server.js +0 -267
  95. package/dist/source/services/youtube-music/api.js +0 -649
  96. package/dist/source/services/youtube-music/search.service.js +0 -38
  97. package/dist/source/stores/history.store.js +0 -64
  98. package/dist/source/stores/navigation.store.js +0 -90
  99. package/dist/source/stores/player.store.js +0 -724
  100. package/dist/source/stores/plugins.store.js +0 -177
  101. package/dist/source/types/actions.js +0 -1
  102. package/dist/source/types/cli.types.js +0 -1
  103. package/dist/source/types/config.types.js +0 -1
  104. package/dist/source/types/history.types.js +0 -1
  105. package/dist/source/types/import.types.js +0 -2
  106. package/dist/source/types/keyboard.types.js +0 -1
  107. package/dist/source/types/navigation.types.js +0 -1
  108. package/dist/source/types/player.types.js +0 -1
  109. package/dist/source/types/playlist.types.js +0 -1
  110. package/dist/source/types/plugin.types.js +0 -1
  111. package/dist/source/types/theme.types.js +0 -1
  112. package/dist/source/types/web.types.js +0 -2
  113. package/dist/source/types/youtube-music.types.js +0 -1
  114. package/dist/source/types/youtubei.types.js +0 -3
  115. package/dist/source/utils/constants.js +0 -134
  116. package/dist/source/utils/format.js +0 -24
  117. package/dist/source/utils/icons.js +0 -26
  118. package/dist/source/utils/search-filters.js +0 -100
@@ -1,290 +0,0 @@
1
- import { logger } from "../logger/logger.service.js";
2
- class WebStreamingService {
3
- clients = new Map();
4
- clientInfo = new Map();
5
- messageHandlers = new Set();
6
- prevState = null;
7
- UPDATE_THROTTLE_MS = 250; // Throttle updates to 4/sec
8
- lastUpdateTime = 0;
9
- pendingUpdate = null;
10
- updateTimer = null;
11
- /**
12
- * Add a client connection
13
- */
14
- addClient(clientId, ws, authenticated = true) {
15
- this.clients.set(clientId, ws);
16
- this.clientInfo.set(clientId, {
17
- id: clientId,
18
- authenticated,
19
- connectedAt: Date.now(),
20
- lastHeartbeat: Date.now(),
21
- });
22
- logger.info('WebStreamingService', 'Client connected', {
23
- clientId,
24
- authenticated,
25
- });
26
- // Send initial state if available
27
- if (this.prevState) {
28
- this.sendToClient(clientId, {
29
- type: 'state-update',
30
- state: this.prevState,
31
- });
32
- }
33
- // Send connection event
34
- this.broadcast({
35
- type: 'event',
36
- event: 'client-connected',
37
- data: { clientId, clientCount: this.clients.size },
38
- });
39
- }
40
- /**
41
- * Remove a client connection
42
- */
43
- removeClient(clientId) {
44
- const hadClient = this.clients.has(clientId);
45
- this.clients.delete(clientId);
46
- this.clientInfo.delete(clientId);
47
- if (hadClient) {
48
- logger.info('WebStreamingService', 'Client disconnected', {
49
- clientId,
50
- remainingClients: this.clients.size,
51
- });
52
- this.broadcast({
53
- type: 'event',
54
- event: 'client-disconnected',
55
- data: { clientId, clientCount: this.clients.size },
56
- });
57
- }
58
- }
59
- /**
60
- * Check if a client exists
61
- */
62
- hasClient(clientId) {
63
- return this.clients.has(clientId);
64
- }
65
- /**
66
- * Get client count
67
- */
68
- getClientCount() {
69
- return this.clients.size;
70
- }
71
- /**
72
- * Get all connected clients
73
- */
74
- getClients() {
75
- return Array.from(this.clients.keys());
76
- }
77
- /**
78
- * Handle incoming message from a client
79
- */
80
- handleClientMessage(clientId, message) {
81
- try {
82
- const msg = message;
83
- // Update client heartbeat
84
- const info = this.clientInfo.get(clientId);
85
- if (info) {
86
- info.lastHeartbeat = Date.now();
87
- this.clientInfo.set(clientId, info);
88
- }
89
- // Emit to all handlers
90
- for (const handler of this.messageHandlers) {
91
- handler(msg);
92
- }
93
- }
94
- catch (error) {
95
- logger.error('WebStreamingService', 'Failed to handle client message', {
96
- clientId,
97
- error: error instanceof Error ? error.message : String(error),
98
- });
99
- }
100
- }
101
- /**
102
- * Register a handler for incoming client messages
103
- */
104
- onMessage(handler) {
105
- this.messageHandlers.add(handler);
106
- return () => {
107
- this.messageHandlers.delete(handler);
108
- };
109
- }
110
- /**
111
- * Send a message to a specific client
112
- */
113
- sendToClient(clientId, message) {
114
- const ws = this.clients.get(clientId);
115
- if (!ws || ws.readyState !== WebSocket.OPEN) {
116
- return;
117
- }
118
- try {
119
- ws.send(JSON.stringify(message));
120
- }
121
- catch (error) {
122
- logger.error('WebStreamingService', 'Failed to send to client', {
123
- clientId,
124
- error: error instanceof Error ? error.message : String(error),
125
- });
126
- }
127
- }
128
- /**
129
- * Broadcast a message to all connected clients
130
- */
131
- broadcast(message) {
132
- const data = JSON.stringify(message);
133
- for (const [clientId, ws] of this.clients) {
134
- if (ws.readyState === WebSocket.OPEN) {
135
- try {
136
- ws.send(data);
137
- }
138
- catch (error) {
139
- logger.error('WebStreamingService', 'Failed to broadcast to client', {
140
- clientId,
141
- error: error instanceof Error ? error.message : String(error),
142
- });
143
- }
144
- }
145
- }
146
- }
147
- /**
148
- * Compute partial state delta (only changed fields)
149
- */
150
- computeDelta(newState) {
151
- if (!this.prevState) {
152
- return newState;
153
- }
154
- const delta = {};
155
- // Check each field for changes
156
- const fields = [
157
- 'currentTrack',
158
- 'isPlaying',
159
- 'volume',
160
- 'speed',
161
- 'progress',
162
- 'duration',
163
- 'queue',
164
- 'queuePosition',
165
- 'repeat',
166
- 'shuffle',
167
- 'isLoading',
168
- 'error',
169
- ];
170
- for (const field of fields) {
171
- const prevValue = this.prevState[field];
172
- const newValue = newState[field];
173
- // Deep comparison for objects/arrays
174
- if (typeof prevValue === 'object' && prevValue !== null) {
175
- if (JSON.stringify(prevValue) !== JSON.stringify(newValue)) {
176
- delta[field] = newValue;
177
- }
178
- }
179
- else if (prevValue !== newValue) {
180
- delta[field] = newValue;
181
- }
182
- }
183
- return delta;
184
- }
185
- /**
186
- * Update and broadcast player state (throttled)
187
- */
188
- onStateChange(state) {
189
- this.prevState = { ...state };
190
- const now = Date.now();
191
- const delta = this.computeDelta(state);
192
- // Skip if no changes
193
- if (Object.keys(delta).length === 0) {
194
- return;
195
- }
196
- // Merge with pending update
197
- this.pendingUpdate = { ...(this.pendingUpdate || {}), ...delta };
198
- // Clear existing timer
199
- if (this.updateTimer) {
200
- clearTimeout(this.updateTimer);
201
- }
202
- // If throttle period passed, send immediately
203
- if (now - this.lastUpdateTime >= this.UPDATE_THROTTLE_MS) {
204
- this.sendPendingUpdate();
205
- }
206
- else {
207
- // Otherwise, schedule update
208
- this.updateTimer = setTimeout(() => {
209
- this.sendPendingUpdate();
210
- }, this.UPDATE_THROTTLE_MS - (now - this.lastUpdateTime));
211
- }
212
- }
213
- /**
214
- * Send pending state update to all clients
215
- */
216
- sendPendingUpdate() {
217
- if (!this.pendingUpdate)
218
- return;
219
- this.broadcast({
220
- type: 'state-update',
221
- state: this.pendingUpdate,
222
- });
223
- this.pendingUpdate = null;
224
- this.lastUpdateTime = Date.now();
225
- }
226
- /**
227
- * Broadcast import progress
228
- */
229
- onImportProgress(progress) {
230
- this.broadcast({
231
- type: 'import-progress',
232
- data: progress,
233
- });
234
- }
235
- /**
236
- * Broadcast import result
237
- */
238
- onImportResult(result) {
239
- this.broadcast({
240
- type: 'import-result',
241
- data: result,
242
- });
243
- }
244
- /**
245
- * Broadcast error message
246
- */
247
- sendError(error, code) {
248
- this.broadcast({
249
- type: 'error',
250
- error,
251
- code,
252
- });
253
- }
254
- /**
255
- * Disconnect all clients
256
- */
257
- disconnectAll() {
258
- for (const [, ws] of this.clients) {
259
- try {
260
- ws.close();
261
- }
262
- catch {
263
- // Ignore
264
- }
265
- }
266
- this.clients.clear();
267
- this.clientInfo.clear();
268
- logger.info('WebStreamingService', 'All clients disconnected');
269
- }
270
- /**
271
- * Get server statistics
272
- */
273
- getStats() {
274
- const now = Date.now();
275
- const oldestClient = Array.from(this.clientInfo.values()).sort((a, b) => a.connectedAt - b.connectedAt)[0];
276
- return {
277
- clients: this.clients.size,
278
- totalConnections: this.clientInfo.size,
279
- uptime: oldestClient ? now - oldestClient.connectedAt : 0,
280
- };
281
- }
282
- }
283
- // Singleton instance
284
- let webStreamingServiceInstance = null;
285
- export function getWebStreamingService() {
286
- if (!webStreamingServiceInstance) {
287
- webStreamingServiceInstance = new WebStreamingService();
288
- }
289
- return webStreamingServiceInstance;
290
- }
@@ -1,267 +0,0 @@
1
- // WebSocket server for web UI
2
- import { createServer as createHttpServer, } from 'node:http';
3
- import { WebSocketServer, WebSocket } from 'ws';
4
- import { getWebStreamingService } from "./web-streaming.service.js";
5
- import { getStaticFileService } from "./static-file.service.js";
6
- import { logger } from "../logger/logger.service.js";
7
- class WebSocketServerClass {
8
- httpServer = null;
9
- wsServer = null;
10
- config;
11
- streamingService = getWebStreamingService();
12
- staticFileService = getStaticFileService();
13
- onCommand;
14
- onImportRequest;
15
- onSearchRequest;
16
- onConfigUpdate;
17
- constructor() {
18
- this.config = {
19
- enabled: false,
20
- host: 'localhost',
21
- port: 8080,
22
- enableCors: true,
23
- allowedOrigins: ['*'],
24
- auth: { enabled: false },
25
- };
26
- }
27
- /**
28
- * Start the WebSocket server
29
- */
30
- async start(options) {
31
- this.config = options.config;
32
- this.onCommand = options.onCommand;
33
- this.onImportRequest = options.onImportRequest;
34
- this.onSearchRequest = options.onSearchRequest;
35
- this.onConfigUpdate = options.onConfigUpdate;
36
- logger.info('WebSocketServer', 'Starting server', {
37
- host: this.config.host,
38
- port: this.config.port,
39
- auth: this.config.auth.enabled,
40
- });
41
- // Create HTTP server
42
- this.httpServer = createHttpServer((req, res) => {
43
- this.handleHttpRequest(req, res);
44
- });
45
- // Create WebSocket server
46
- this.wsServer = new WebSocketServer({
47
- server: this.httpServer,
48
- path: '/ws',
49
- });
50
- // Handle WebSocket connections
51
- this.wsServer.on('connection', (ws, req) => {
52
- this.handleWebSocketConnection(ws, req);
53
- });
54
- // Handle HTTP server errors
55
- this.httpServer.on('error', error => {
56
- logger.error('WebSocketServer', 'HTTP server error', {
57
- error: error instanceof Error ? error.message : String(error),
58
- });
59
- });
60
- // Handle WebSocket server errors
61
- this.wsServer.on('error', error => {
62
- logger.error('WebSocketServer', 'WebSocket server error', {
63
- error: error instanceof Error ? error.message : String(error),
64
- });
65
- });
66
- // Start listening
67
- return new Promise((resolve, reject) => {
68
- this.httpServer.listen({
69
- host: this.config.host,
70
- port: this.config.port,
71
- }, () => {
72
- logger.info('WebSocketServer', 'Server started', {
73
- url: `http://${this.config.host}:${this.config.port}`,
74
- });
75
- resolve();
76
- });
77
- this.httpServer.on('error', reject);
78
- });
79
- }
80
- /**
81
- * Handle HTTP requests (for static file serving)
82
- */
83
- handleHttpRequest(req, res) {
84
- // Set CORS headers if enabled
85
- if (this.config.enableCors) {
86
- const origin = req.headers.origin;
87
- if (origin &&
88
- (this.config.allowedOrigins.includes('*') ||
89
- this.config.allowedOrigins.includes(origin))) {
90
- res.setHeader('Access-Control-Allow-Origin', origin);
91
- res.setHeader('Access-Control-Allow-Methods', 'GET, POST, OPTIONS');
92
- res.setHeader('Access-Control-Allow-Headers', 'Content-Type, Authorization');
93
- }
94
- }
95
- // Handle preflight requests
96
- if (req.method === 'OPTIONS') {
97
- res.writeHead(204);
98
- res.end();
99
- return;
100
- }
101
- // Serve static files
102
- const url = req.url ?? '/';
103
- this.staticFileService.serve(url, req, res);
104
- }
105
- /**
106
- * Handle WebSocket connection
107
- */
108
- handleWebSocketConnection(ws, req) {
109
- const clientId = this.generateClientId();
110
- logger.info('WebSocketServer', 'New connection', {
111
- clientId,
112
- ip: req.socket.remoteAddress,
113
- });
114
- // Handle authentication if enabled
115
- if (this.config.auth.enabled) {
116
- const token = this.extractAuthToken(req);
117
- if (!token || token !== this.config.auth.token) {
118
- logger.warn('WebSocketServer', 'Authentication failed', { clientId });
119
- ws.close(1008, 'Authentication failed');
120
- return;
121
- }
122
- }
123
- // Add client to streaming service
124
- this.streamingService.addClient(clientId, ws, true);
125
- // Send welcome message
126
- this.sendToClient(ws, {
127
- type: 'auth',
128
- success: true,
129
- message: 'Connected to YouTube Music CLI',
130
- });
131
- // Handle incoming messages
132
- ws.on('message', (data) => {
133
- try {
134
- const message = JSON.parse(data.toString());
135
- this.streamingService.handleClientMessage(clientId, message);
136
- this.handleClientCommand(clientId, message);
137
- }
138
- catch (error) {
139
- logger.error('WebSocketServer', 'Failed to parse message', {
140
- clientId,
141
- error: error instanceof Error ? error.message : String(error),
142
- });
143
- }
144
- });
145
- // Handle close
146
- ws.on('close', () => {
147
- this.streamingService.removeClient(clientId);
148
- });
149
- // Handle errors
150
- ws.on('error', error => {
151
- logger.error('WebSocketServer', 'WebSocket error', {
152
- error: error instanceof Error ? error.message : String(error),
153
- });
154
- });
155
- }
156
- /**
157
- * Handle commands from clients
158
- */
159
- handleClientCommand(_clientId, message) {
160
- switch (message.type) {
161
- case 'command':
162
- if (this.onCommand) {
163
- this.onCommand(message.action);
164
- }
165
- break;
166
- case 'import-request':
167
- if (this.onImportRequest) {
168
- this.onImportRequest(message.source, message.url, message.name);
169
- }
170
- break;
171
- case 'search-request':
172
- if (this.onSearchRequest) {
173
- this.onSearchRequest(message.query, message.searchType);
174
- }
175
- break;
176
- case 'config-update':
177
- if (this.onConfigUpdate) {
178
- this.onConfigUpdate(message.config);
179
- }
180
- break;
181
- case 'auth-request':
182
- // Already handled in connection phase
183
- break;
184
- }
185
- }
186
- /**
187
- * Send message to a specific WebSocket client
188
- */
189
- sendToClient(ws, message) {
190
- if (ws.readyState === WebSocket.OPEN) {
191
- try {
192
- ws.send(JSON.stringify(message));
193
- }
194
- catch (error) {
195
- logger.error('WebSocketServer', 'Failed to send message', {
196
- error: error instanceof Error ? error.message : String(error),
197
- });
198
- }
199
- }
200
- }
201
- /**
202
- * Generate a unique client ID
203
- */
204
- generateClientId() {
205
- return `client_${Date.now()}_${Math.random().toString(36).substring(2, 9)}`;
206
- }
207
- /**
208
- * Extract auth token from request
209
- */
210
- extractAuthToken(req) {
211
- // Check Authorization header
212
- const authHeader = req.headers.authorization;
213
- if (authHeader?.startsWith('Bearer ')) {
214
- return authHeader.substring(7);
215
- }
216
- // Check query parameter
217
- const url = req.url ?? '';
218
- const urlObj = new URL(url, `http://${req.headers.host}`);
219
- return urlObj.searchParams.get('token');
220
- }
221
- /**
222
- * Stop the server
223
- */
224
- async stop() {
225
- logger.info('WebSocketServer', 'Stopping server');
226
- // Disconnect all clients
227
- this.streamingService.disconnectAll();
228
- // Close WebSocket server
229
- if (this.wsServer) {
230
- this.wsServer.close();
231
- this.wsServer = null;
232
- }
233
- // Close HTTP server
234
- if (this.httpServer) {
235
- return new Promise(resolve => {
236
- this.httpServer.close(() => {
237
- this.httpServer = null;
238
- logger.info('WebSocketServer', 'Server stopped');
239
- resolve();
240
- });
241
- });
242
- }
243
- }
244
- /**
245
- * Check if server is running
246
- */
247
- isRunning() {
248
- return this.httpServer !== null;
249
- }
250
- /**
251
- * Get server URL
252
- */
253
- getServerUrl() {
254
- if (!this.isRunning()) {
255
- throw new Error('Server is not running');
256
- }
257
- return `http://${this.config.host}:${this.config.port}`;
258
- }
259
- }
260
- // Singleton instance
261
- let webSocketServerInstance = null;
262
- export function getWebSocketServer() {
263
- if (!webSocketServerInstance) {
264
- webSocketServerInstance = new WebSocketServerClass();
265
- }
266
- return webSocketServerInstance;
267
- }