1+ import { BaseComponent } from './base-component.js' ;
2+ import WebSocketClient from '../utils/websocket-client.js' ;
3+
4+ /**
5+ * WebSocket Example Component
6+ *
7+ * This component demonstrates how to use the WebSocketClient utility
8+ * to establish a WebSocket connection and exchange messages with the server.
9+ */
10+ class WebSocketExample extends BaseComponent {
11+ constructor ( ) {
12+ super ( ) ;
13+
14+ // Initialize WebSocketClient
15+ this . wsClient = new WebSocketClient ( {
16+ port : 8100 ,
17+ endpoint : '' ,
18+ reconnectInterval : 3000 ,
19+ maxReconnectAttempts : 3
20+ } ) ;
21+
22+ // Bind methods
23+ this . handleConnect = this . handleConnect . bind ( this ) ;
24+ this . handleDisconnect = this . handleDisconnect . bind ( this ) ;
25+ this . handleSendMessage = this . handleSendMessage . bind ( this ) ;
26+ this . handleMessageInput = this . handleMessageInput . bind ( this ) ;
27+ this . handleWebSocketMessage = this . handleWebSocketMessage . bind ( this ) ;
28+ this . handleWebSocketOpen = this . handleWebSocketOpen . bind ( this ) ;
29+ this . handleWebSocketClose = this . handleWebSocketClose . bind ( this ) ;
30+ this . handleWebSocketError = this . handleWebSocketError . bind ( this ) ;
31+ this . handleWebSocketReconnect = this . handleWebSocketReconnect . bind ( this ) ;
32+ this . handleWebSocketReconnectFailed = this . handleWebSocketReconnectFailed . bind ( this ) ;
33+
34+ // Register WebSocket event listeners
35+ this . wsClient . on ( 'message' , this . handleWebSocketMessage ) ;
36+ this . wsClient . on ( 'open' , this . handleWebSocketOpen ) ;
37+ this . wsClient . on ( 'close' , this . handleWebSocketClose ) ;
38+ this . wsClient . on ( 'error' , this . handleWebSocketError ) ;
39+ this . wsClient . on ( 'reconnect' , this . handleWebSocketReconnect ) ;
40+ this . wsClient . on ( 'reconnectFailed' , this . handleWebSocketReconnectFailed ) ;
41+ }
42+
43+ /**
44+ * Component template
45+ */
46+ template ( ) {
47+ return `
48+ <div class="websocket-example">
49+ <h2>WebSocket Example</h2>
50+
51+ <div class="connection-status">
52+ Status: <span id="status" class="status-disconnected">Disconnected</span>
53+ </div>
54+
55+ <div class="connection-controls">
56+ <button id="connectBtn" class="btn">Connect</button>
57+ <button id="disconnectBtn" class="btn" disabled>Disconnect</button>
58+ </div>
59+
60+ <div class="message-container">
61+ <h3>Messages</h3>
62+ <div id="messages" class="messages"></div>
63+ </div>
64+
65+ <div class="message-input">
66+ <input type="text" id="messageInput" placeholder="Type a message..." disabled>
67+ <button id="sendBtn" class="btn" disabled>Send</button>
68+ </div>
69+ </div>
70+ ` ;
71+ }
72+
73+ /**
74+ * Component styles
75+ */
76+ styles ( ) {
77+ return `
78+ .websocket-example {
79+ font-family: Arial, sans-serif;
80+ max-width: 600px;
81+ margin: 0 auto;
82+ padding: 20px;
83+ border: 1px solid #ddd;
84+ border-radius: 5px;
85+ }
86+
87+ .connection-status {
88+ margin-bottom: 10px;
89+ }
90+
91+ .status-connected {
92+ color: green;
93+ font-weight: bold;
94+ }
95+
96+ .status-disconnected {
97+ color: red;
98+ }
99+
100+ .status-connecting {
101+ color: orange;
102+ }
103+
104+ .connection-controls {
105+ margin-bottom: 20px;
106+ }
107+
108+ .btn {
109+ padding: 8px 16px;
110+ margin-right: 10px;
111+ background-color: #4caf50;
112+ color: white;
113+ border: none;
114+ border-radius: 4px;
115+ cursor: pointer;
116+ }
117+
118+ .btn:hover {
119+ background-color: #45a049;
120+ }
121+
122+ .btn:disabled {
123+ background-color: #cccccc;
124+ cursor: not-allowed;
125+ }
126+
127+ .messages {
128+ border: 1px solid #ddd;
129+ padding: 10px;
130+ height: 200px;
131+ overflow-y: auto;
132+ margin-bottom: 10px;
133+ background-color: #f9f9f9;
134+ }
135+
136+ .message {
137+ margin-bottom: 5px;
138+ padding: 5px;
139+ border-radius: 4px;
140+ }
141+
142+ .message-received {
143+ background-color: #e3f2fd;
144+ }
145+
146+ .message-sent {
147+ background-color: #e8f5e9;
148+ text-align: right;
149+ }
150+
151+ .message-system {
152+ background-color: #fff3e0;
153+ font-style: italic;
154+ }
155+
156+ .message-input {
157+ display: flex;
158+ }
159+
160+ #messageInput {
161+ flex-grow: 1;
162+ padding: 8px;
163+ margin-right: 10px;
164+ border: 1px solid #ddd;
165+ border-radius: 4px;
166+ }
167+ ` ;
168+ }
169+
170+ /**
171+ * Called when the component is connected to the DOM
172+ */
173+ connectedCallback ( ) {
174+ super . connectedCallback ( ) ;
175+
176+ // Get DOM elements
177+ this . statusElement = this . shadowRoot . getElementById ( 'status' ) ;
178+ this . connectButton = this . shadowRoot . getElementById ( 'connectBtn' ) ;
179+ this . disconnectButton = this . shadowRoot . getElementById ( 'disconnectBtn' ) ;
180+ this . messageInput = this . shadowRoot . getElementById ( 'messageInput' ) ;
181+ this . sendButton = this . shadowRoot . getElementById ( 'sendBtn' ) ;
182+ this . messagesContainer = this . shadowRoot . getElementById ( 'messages' ) ;
183+
184+ // Add event listeners
185+ this . connectButton . addEventListener ( 'click' , this . handleConnect ) ;
186+ this . disconnectButton . addEventListener ( 'click' , this . handleDisconnect ) ;
187+ this . sendButton . addEventListener ( 'click' , this . handleSendMessage ) ;
188+ this . messageInput . addEventListener ( 'keypress' , this . handleMessageInput ) ;
189+ }
190+
191+ /**
192+ * Called when the component is disconnected from the DOM
193+ */
194+ disconnectedCallback ( ) {
195+ // Remove event listeners
196+ this . connectButton . removeEventListener ( 'click' , this . handleConnect ) ;
197+ this . disconnectButton . removeEventListener ( 'click' , this . handleDisconnect ) ;
198+ this . sendButton . removeEventListener ( 'click' , this . handleSendMessage ) ;
199+ this . messageInput . removeEventListener ( 'keypress' , this . handleMessageInput ) ;
200+
201+ // Disconnect WebSocket
202+ this . wsClient . disconnect ( ) ;
203+
204+ // Remove WebSocket event listeners
205+ this . wsClient . off ( 'message' , this . handleWebSocketMessage ) ;
206+ this . wsClient . off ( 'open' , this . handleWebSocketOpen ) ;
207+ this . wsClient . off ( 'close' , this . handleWebSocketClose ) ;
208+ this . wsClient . off ( 'error' , this . handleWebSocketError ) ;
209+ this . wsClient . off ( 'reconnect' , this . handleWebSocketReconnect ) ;
210+ this . wsClient . off ( 'reconnectFailed' , this . handleWebSocketReconnectFailed ) ;
211+
212+ super . disconnectedCallback ( ) ;
213+ }
214+
215+ /**
216+ * Handle connect button click
217+ */
218+ handleConnect ( ) {
219+ this . updateStatus ( 'Connecting...' , 'status-connecting' ) ;
220+ this . addMessage ( 'Connecting to WebSocket server...' , 'system' ) ;
221+
222+ this . wsClient . connect ( )
223+ . catch ( error => {
224+ console . error ( 'Failed to connect:' , error ) ;
225+ this . updateStatus ( 'Connection failed' , 'status-disconnected' ) ;
226+ this . addMessage ( `Connection failed: ${ error . message } ` , 'system' ) ;
227+ } ) ;
228+ }
229+
230+ /**
231+ * Handle disconnect button click
232+ */
233+ handleDisconnect ( ) {
234+ this . wsClient . disconnect ( ) ;
235+ }
236+
237+ /**
238+ * Handle send button click
239+ */
240+ handleSendMessage ( ) {
241+ const message = this . messageInput . value . trim ( ) ;
242+
243+ if ( message && this . wsClient . isConnected ( ) ) {
244+ this . wsClient . send ( message ) ;
245+ this . addMessage ( message , 'sent' ) ;
246+ this . messageInput . value = '' ;
247+ }
248+ }
249+
250+ /**
251+ * Handle message input keypress
252+ */
253+ handleMessageInput ( event ) {
254+ if ( event . key === 'Enter' ) {
255+ this . handleSendMessage ( ) ;
256+ }
257+ }
258+
259+ /**
260+ * Handle WebSocket message event
261+ */
262+ handleWebSocketMessage ( data ) {
263+ this . addMessage ( data , 'received' ) ;
264+ }
265+
266+ /**
267+ * Handle WebSocket open event
268+ */
269+ handleWebSocketOpen ( ) {
270+ this . updateStatus ( 'Connected' , 'status-connected' ) ;
271+ this . addMessage ( 'Connected to WebSocket server' , 'system' ) ;
272+
273+ // Update UI
274+ this . connectButton . disabled = true ;
275+ this . disconnectButton . disabled = false ;
276+ this . messageInput . disabled = false ;
277+ this . sendButton . disabled = false ;
278+ }
279+
280+ /**
281+ * Handle WebSocket close event
282+ */
283+ handleWebSocketClose ( event ) {
284+ this . updateStatus ( 'Disconnected' , 'status-disconnected' ) ;
285+ this . addMessage ( `Disconnected from server: ${ event . reason || 'Connection closed' } ` , 'system' ) ;
286+
287+ // Update UI
288+ this . connectButton . disabled = false ;
289+ this . disconnectButton . disabled = true ;
290+ this . messageInput . disabled = true ;
291+ this . sendButton . disabled = true ;
292+ }
293+
294+ /**
295+ * Handle WebSocket error event
296+ */
297+ handleWebSocketError ( ) {
298+ this . addMessage ( 'WebSocket error occurred' , 'system' ) ;
299+ }
300+
301+ /**
302+ * Handle WebSocket reconnect event
303+ */
304+ handleWebSocketReconnect ( attempt ) {
305+ this . updateStatus ( `Reconnecting (${ attempt } )...` , 'status-connecting' ) ;
306+ this . addMessage ( `Attempting to reconnect (${ attempt } )...` , 'system' ) ;
307+ }
308+
309+ /**
310+ * Handle WebSocket reconnect failed event
311+ */
312+ handleWebSocketReconnectFailed ( ) {
313+ this . updateStatus ( 'Reconnection failed' , 'status-disconnected' ) ;
314+ this . addMessage ( 'Failed to reconnect after multiple attempts' , 'system' ) ;
315+ }
316+
317+ /**
318+ * Update the connection status
319+ */
320+ updateStatus ( text , className ) {
321+ this . statusElement . textContent = text ;
322+ this . statusElement . className = className ;
323+ }
324+
325+ /**
326+ * Add a message to the messages container
327+ */
328+ addMessage ( text , type ) {
329+ const messageElement = document . createElement ( 'div' ) ;
330+ messageElement . classList . add ( 'message' , `message-${ type } ` ) ;
331+ messageElement . textContent = text ;
332+ this . messagesContainer . appendChild ( messageElement ) ;
333+ this . messagesContainer . scrollTop = this . messagesContainer . scrollHeight ;
334+ }
335+ }
336+
337+ // Define the custom element
338+ customElements . define ( 'websocket-example' , WebSocketExample ) ;
339+
340+ export default WebSocketExample ;
0 commit comments