diff options
author | Zhongheng Liu <z.liu@outlook.com.gr> | 2023-12-21 19:07:06 +0200 |
---|---|---|
committer | Zhongheng Liu <z.liu@outlook.com.gr> | 2023-12-21 19:07:06 +0200 |
commit | 6fc628aee3bf74351244df69594bab2ec66aa9d8 (patch) | |
tree | f434da047be492dc043069e3ff04b494e2d84a18 | |
parent | 1fbd9556524dffdff91bffdec3fc8a884fcffaea (diff) | |
download | epq-web-6fc628aee3bf74351244df69594bab2ec66aa9d8.tar.gz epq-web-6fc628aee3bf74351244df69594bab2ec66aa9d8.tar.bz2 epq-web-6fc628aee3bf74351244df69594bab2ec66aa9d8.zip |
Temporary solution: renderToStaticMarkup
-rw-r--r-- | .vscode/launch.json | 20 | ||||
-rw-r--r-- | src/App.tsx | 11 | ||||
-rw-r--r-- | src/Chat/Chat.tsx | 80 | ||||
-rw-r--r-- | src/Chat/Message.tsx | 2 | ||||
-rw-r--r-- | src/Chat/Socket.tsx | 61 | ||||
-rw-r--r-- | src/index.tsx | 2 |
6 files changed, 118 insertions, 58 deletions
diff --git a/.vscode/launch.json b/.vscode/launch.json new file mode 100644 index 0000000..0853fbc --- /dev/null +++ b/.vscode/launch.json @@ -0,0 +1,20 @@ +{ + // Use IntelliSense to learn about possible attributes. + // Hover to view descriptions of existing attributes. + // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 + "version": "0.2.0", + "configurations": [ + { + "type": "node", + "request": "launch", + "name": "Launch Program", + "skipFiles": [ + "<node_internals>/**" + ], + "program": "${workspaceFolder}/src/Chat/Chat.tsx", + "outFiles": [ + "${workspaceFolder}/**/*.js" + ] + } + ] +}
\ No newline at end of file diff --git a/src/App.tsx b/src/App.tsx index 84234b7..56cd405 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -1,16 +1,17 @@ -import React from "react"; +import React, { useState } from "react"; import ChatWrapper from "./Chat/Chat"; const App = (): React.ReactElement => { - var username: string | null = prompt("Username: ") + const [username, setUsername] = useState<string>() if (!username) { - alert("Invalid username!") - var username: string | null = prompt("Username: ") + const newName = prompt("Username:") as string + setUsername(newName) } return ( <div className="App"> <h1>Local Area Network Chat Application</h1> <pre>This web application was built for the purposes of an EPQ project.</pre> - <ChatWrapper user={username as string} brokerURL=""/> + + {<ChatWrapper user={username as string} brokerURL=""/> } </div> ) } diff --git a/src/Chat/Chat.tsx b/src/Chat/Chat.tsx index 817ada2..080ea71 100644 --- a/src/Chat/Chat.tsx +++ b/src/Chat/Chat.tsx @@ -1,9 +1,11 @@ -import React, { useState } from "react"; +import React, { useEffect, useState } from "react"; import { Message } from "./Message"; import { Client, Stomp } from "@stomp/stompjs"; import { MessageType } from "./types"; -import useWebSocket from "react-use-websocket"; - +import { renderToStaticMarkup } from 'react-dom/server'; +const domain = "localhost" +const port = "8080" +const connectionAddress = `ws://${domain}:${port}/ws` const ChatWrapper = ( { user, @@ -14,24 +16,23 @@ const ChatWrapper = ( brokerURL: string, } ): React.ReactElement => { - const domain = "localhost" - const port = "8080" - const connectionAddress = `ws://${domain}:${port}/ws` const stompClient = new Client({ brokerURL: connectionAddress }) - const [destination, setDestination] = useState<string>("/app/chat") - const [connected, setConnected] = useState(false) - const [subscribe, setSubscribe] = useState("/sub/chat") - const [username, setUsername] = useState<string>(user) - const [children, setChildren] = useState<React.ReactElement>() + const destination = "/app/chat" + const subscribe = "/sub/chat" + // const [children, setChildren] = useState<React.ReactElement[]>([]) stompClient.onConnect = (frame) => { - setConnected(true); stompClient.subscribe(subscribe, (message) => { console.log(`Collected new message: ${message.body}`); const {from, to, content} = JSON.parse(message.body) as MessageType const messageElement = <Message sender={from} text={content} /> - setChildren(messageElement) + // setChildren((prev) => [...prev, messageElement]) + console.log(messageElement); + + // Temporary solution + const container = document.getElementById("chat-inner") as HTMLDivElement + container.innerHTML += renderToStaticMarkup(messageElement) }) } stompClient.onWebSocketError = (error) => { @@ -42,58 +43,37 @@ const ChatWrapper = ( console.error('Broker reported error: ' + frame.headers['message']); console.error('Additional details: ' + frame.body); }; + const sendDataButtonHandler = (ev: React.MouseEvent) => { console.log("WebSockets handler invoked.") - ev.preventDefault() + const entryElement: HTMLInputElement = document.getElementById("data-entry") as HTMLInputElement const messageData = { - from: username, + from: user, to: "everyone", content: entryElement.value } console.log(`STOMP connection status: ${stompClient.connected}`); - if (stompClient.connected) { - stompClient.publish({ - body: JSON.stringify(messageData), - destination: destination - }) - } else {alert("STOMP not activated!")} + stompClient.publish({ + body: JSON.stringify(messageData), + destination: destination + }) + ev.preventDefault() } - const connect = () => { + useEffect(() => { stompClient.activate() - } - const disconnect = () => { - stompClient.deactivate() - } - // connection.addEventListener("open", (ev: Event) => { - // ev.preventDefault() - // connection.send("Hello world!") - // }) - // connection.addEventListener("message", (ev: MessageEvent) => { - // ev.preventDefault() - // const wrappers = document.getElementsByClassName(msgWrapperClassName) - - // // Matches data from JSON data input against ChatMessage datatype for processing - // const data = JSON.parse(ev.data) as ChatMessage - // for (let index = 0; index < wrappers.length; index++) { - // const element: Element | null = wrappers.item(index); - // if (!element) { - // console.error("msgWrapper class cannot be found! Message not delivered.") - // return - // } - // messageElementsArray.push(<Message sender={data.from} text={data.message} />) - // // TODO Create new message - // // DDL 20 DEC - // } - // }) + return () => { + stompClient.deactivate() + } + }, []) return ( <div className="chat"> - <button onClick={ev => connect()} disabled={false}>Connect</button> - <button onClick={ev => disconnect()} disabled={!connected}>Disconnect</button> + {/* <button onClick={ev => {connect()}} disabled={connected}>Connect</button> + <button onClick={ev => {disconnect()}} disabled={!connected}>Disconnect</button> */} <div id="chat-inner"> - {children} + {/* {children} */} </div> <span><input id="data-entry"></input><button onClick={ev => sendDataButtonHandler(ev)}>Send</button></span> </div> diff --git a/src/Chat/Message.tsx b/src/Chat/Message.tsx index 9299ff8..ec89348 100644 --- a/src/Chat/Message.tsx +++ b/src/Chat/Message.tsx @@ -9,5 +9,5 @@ export const Message = ( } ): React.ReactElement<{ sender: string; text: string; }> => { - return (<p>Message from {sender} @ {}: {text}</p>); + return (<p>Message from {sender}: {text}</p>); }; diff --git a/src/Chat/Socket.tsx b/src/Chat/Socket.tsx new file mode 100644 index 0000000..cbb4e10 --- /dev/null +++ b/src/Chat/Socket.tsx @@ -0,0 +1,61 @@ +import { Client } from "@stomp/stompjs" +import { useState } from "react" +import { Message } from "./Message" +import { MessageType } from "./types" + +const Socket = ( + { + address, + user, + messageCallback, + }: + { + address: string, + user: string, + messageCallback: (element: JSX.Element) => {}, + } +) => { + const stompClient = new Client({ + brokerURL: address + }) + const destination = "/app/chat" + const subscribe = "/sub/chat" + stompClient.onConnect = (frame) => { + stompClient.subscribe(subscribe, (message) => { + console.log(`Collected new message: ${message.body}`); + const {from, to, content} = JSON.parse(message.body) as MessageType + const messageElement = <Message sender={from} text={content} /> + // return message to parent + messageCallback(messageElement) + }) + } + stompClient.onWebSocketError = (error) => { + console.error('Error with websocket', error); + }; + + stompClient.onStompError = (frame) => { + console.error('Broker reported error: ' + frame.headers['message']); + console.error('Additional details: ' + frame.body); + }; + + const send = () => { + console.log("WebSockets handler invoked.") + + const entryElement: HTMLInputElement = document.getElementById("data-entry") as HTMLInputElement + const messageData = + { + from: user, + to: "everyone", + content: entryElement.value + } + console.log(`STOMP connection status: ${stompClient.connected}`); + + stompClient.publish({ + body: JSON.stringify(messageData), + destination: destination + }) + } + stompClient.activate() + return (<></>) +} +export default Socket;
\ No newline at end of file diff --git a/src/index.tsx b/src/index.tsx index 23b3422..1dafd93 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -7,7 +7,5 @@ const root = ReactDOM.createRoot( document.getElementById('root') as HTMLElement ); root.render( - <React.StrictMode> <App /> - </React.StrictMode> );
\ No newline at end of file |