Skip to content

Commit

Permalink
Use React hook to deal with websocket
Browse files Browse the repository at this point in the history
  • Loading branch information
ramondeklein committed Apr 18, 2024
1 parent 6cfb6ff commit 2f96f07
Show file tree
Hide file tree
Showing 3 changed files with 73 additions and 127 deletions.
1 change: 1 addition & 0 deletions web-app/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
"react-pdf": "7.7.1",
"react-redux": "^8.1.3",
"react-router-dom": "6.22.3",
"react-use-websocket": "^4.8.1",
"react-virtualized": "^9.22.5",
"react-window": "^1.8.10",
"react-window-infinite-loader": "^1.0.9",
Expand Down
163 changes: 64 additions & 99 deletions web-app/src/screens/Console/Trace/Trace.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
// You should have received a copy of the GNU Affero General Public License
// along with this program. If not, see <http://www.gnu.org/licenses/>.

import React, { Fragment, useEffect, useState } from "react";
import { Fragment, useEffect, useState } from "react";
import { DateTime } from "luxon";
import { useSelector } from "react-redux";
import {
Expand All @@ -37,20 +37,17 @@ import {
traceMessageReceived,
traceResetMessages,
} from "./traceSlice";
import { setHelpName } from "../../../systemSlice";
import { setHelpName } from "systemSlice";
import TooltipWrapper from "../Common/TooltipWrapper/TooltipWrapper";
import PageHeaderWrapper from "../Common/PageHeaderWrapper/PageHeaderWrapper";
import HelpMenu from "../HelpMenu";

var socket: any = null;
import useWebSocket, { ReadyState } from "react-use-websocket";

const Trace = () => {
const dispatch = useAppDispatch();

const messages = useSelector((state: AppState) => state.trace.messages);
const traceStarted = useSelector(
(state: AppState) => state.trace.traceStarted,
);
const traceStarted = useSelector((state: AppState) => state.trace.traceStarted);

const [statusCode, setStatusCode] = useState<string>("");
const [method, setMethod] = useState<string>("");
Expand All @@ -65,74 +62,66 @@ const Trace = () => {
const [errors, setErrors] = useState<boolean>(false);

const [toggleFilter, setToggleFilter] = useState<boolean>(false);
const [logActive, setLogActive] = useState(false);
const [wsUrl, setWsUrl] = useState<string>("");

const startTrace = () => {
dispatch(traceResetMessages());
useEffect(() => {
const url = new URL(window.location.toString());
const isDev = process.env.NODE_ENV === "development";
const port = isDev ? "9090" : url.port;

let calls = `${s3 ? "s3," : ""}${internal ? "internal," : ""}${
storage ? "storage," : ""
}${os ? "os," : ""}`;
const wsProt = wsProtocol(url.protocol);
const port = process.env.NODE_ENV === "development" ? "9090" : url.port;
const calls = all ? "all" : (() => {
const c = [];
if (s3) c.push("s3");
if (internal) c.push("internal");
if (storage) c.push("storage");
if (os) c.push("os");
return c.join(',');
})();

if (all) {
calls = "all";
}
// check if we are using base path, if not this always is `/`
const baseLocation = new URL(document.baseURI);
const baseUrl = baseLocation.pathname;
const baseLocation = new URL(document.baseURI).pathname;

const wsProt = wsProtocol(url.protocol);
socket = new WebSocket(
`${wsProt}://${
url.hostname
}:${port}${baseUrl}ws/trace?calls=${calls}&threshold=${threshold}&onlyErrors=${
errors ? "yes" : "no"
}&statusCode=${statusCode}&method=${method}&funcname=${func}&path=${path}`,
);
const wsUrl = new URL(`${wsProt}://${url.hostname}:${port}${baseLocation}ws/trace`);
wsUrl.searchParams.append("calls", calls);
wsUrl.searchParams.append("threshold", threshold.toString());
wsUrl.searchParams.append("onlyErrors", errors ? "yes" : "no");
wsUrl.searchParams.append("statusCode", statusCode);
wsUrl.searchParams.append("method", method);
wsUrl.searchParams.append("funcname", func);
wsUrl.searchParams.append("path", path);
setWsUrl(wsUrl.href);
}, [all, s3, internal, storage, os, threshold, errors, statusCode, method, func, path]);

let interval: any | null = null;
if (socket !== null) {
socket.onopen = () => {
console.log("WebSocket Client Connected");
dispatch(setTraceStarted(true));
socket.send("ok");
interval = setInterval(() => {
socket.send("ok");
}, 10 * 1000);
};
socket.onmessage = (message: MessageEvent) => {
let m: TraceMessage = JSON.parse(message.data.toString());
const {sendMessage, lastJsonMessage, readyState} = useWebSocket<TraceMessage>(wsUrl, {
heartbeat: {
message: "ok", interval: 10 * 1000, // send ok every 10 seconds
timeout: 365 * 24 * 60 * 60 * 1000, // disconnect after 365 days (workaround, because heartbeat gets no response)
}
}, logActive);

m.ptime = DateTime.fromISO(m.time).toJSDate();
m.key = Math.random();
dispatch(traceMessageReceived(m));
};
socket.onclose = () => {
clearInterval(interval);
console.log("connection closed by server");
dispatch(setTraceStarted(false));
};
return () => {
socket.close(1000);
clearInterval(interval);
console.log("closing websockets");
setTraceStarted(false);
};
useEffect(() => {
if (readyState === ReadyState.CONNECTING) {
dispatch(traceResetMessages());
} else if (readyState === ReadyState.OPEN) {
dispatch(setTraceStarted(true));
} else if (readyState === ReadyState.CLOSED) {
dispatch(setTraceStarted(false));
}
};
}, [readyState, dispatch, sendMessage]);

const stopTrace = () => {
socket.close(1000);
dispatch(setTraceStarted(false));
};
useEffect(() => {
if (lastJsonMessage) {
lastJsonMessage.ptime = DateTime.fromISO(lastJsonMessage.time).toJSDate();
lastJsonMessage.key = Math.random();
dispatch(traceMessageReceived(lastJsonMessage));
}
}, [lastJsonMessage, dispatch])

useEffect(() => {
dispatch(setHelpName("trace"));
// eslint-disable-next-line react-hooks/exhaustive-deps
}, []);

return (
<Fragment>
<PageHeaderWrapper label={"Trace"} actions={<HelpMenu />} />
Expand Down Expand Up @@ -187,9 +176,7 @@ const Trace = () => {
id={"all_calls"}
name={"all_calls"}
label={"All"}
onChange={() => {
setAll(!all);
}}
onChange={() => setAll(!all)}
value={"all"}
disabled={traceStarted}
/>
Expand All @@ -198,9 +185,7 @@ const Trace = () => {
id={"s3_calls"}
name={"s3_calls"}
label={"S3"}
onChange={() => {
setS3(!s3);
}}
onChange={() => setS3(!s3)}
value={"s3"}
disabled={all || traceStarted}
/>
Expand All @@ -209,9 +194,7 @@ const Trace = () => {
id={"internal_calls"}
name={"internal_calls"}
label={"Internal"}
onChange={() => {
setInternal(!internal);
}}
onChange={() => setInternal(!internal)}
value={"internal"}
disabled={all || traceStarted}
/>
Expand All @@ -220,9 +203,7 @@ const Trace = () => {
id={"storage_calls"}
name={"storage_calls"}
label={"Storage"}
onChange={() => {
setStorage(!storage);
}}
onChange={() => setStorage(!storage)}
value={"storage"}
disabled={all || traceStarted}
/>
Expand All @@ -231,9 +212,7 @@ const Trace = () => {
id={"os_calls"}
name={"os_calls"}
label={"OS"}
onChange={() => {
setOS(!os);
}}
onChange={() => setOS(!os)}
value={"os"}
disabled={all || traceStarted}
/>
Expand All @@ -249,9 +228,7 @@ const Trace = () => {
<TooltipWrapper tooltip={"More filter options"}>
<Button
id={"filter-toggle"}
onClick={() => {
setToggleFilter(!toggleFilter);
}}
onClick={() => setToggleFilter(!toggleFilter)}
label={"Filters"}
icon={<FilterIcon />}
variant={"regular"}
Expand All @@ -269,7 +246,7 @@ const Trace = () => {
label={"Start"}
data-test-id={"trace-start-button"}
variant="callAction"
onClick={startTrace}
onClick={() => setLogActive(true)}
style={{
width: "118px",
}}
Expand All @@ -281,7 +258,7 @@ const Trace = () => {
label={"Stop Trace"}
data-test-id={"trace-stop-button"}
variant="callAction"
onClick={stopTrace}
onClick={() => setLogActive(false)}
style={{
width: "118px",
}}
Expand Down Expand Up @@ -330,9 +307,7 @@ const Trace = () => {
label="Status Code"
placeholder="e.g. 503"
value={statusCode}
onChange={(e) => {
setStatusCode(e.target.value);
}}
onChange={(e) => setStatusCode(e.target.value)}
disabled={traceStarted}
/>

Expand All @@ -343,9 +318,7 @@ const Trace = () => {
label="Function Name"
placeholder="e.g. FunctionName2055"
value={func}
onChange={(e) => {
setFunc(e.target.value);
}}
onChange={(e) => setFunc(e.target.value)}
disabled={traceStarted}
/>

Expand All @@ -356,9 +329,7 @@ const Trace = () => {
label="Method"
placeholder="e.g. Method 2056"
value={method}
onChange={(e) => {
setMethod(e.target.value);
}}
onChange={(e) => setMethod(e.target.value)}
disabled={traceStarted}
/>
</Box>
Expand All @@ -384,9 +355,7 @@ const Trace = () => {
label="Path"
placeholder="e.g. my-bucket/my-prefix/*"
value={path}
onChange={(e) => {
setPath(e.target.value);
}}
onChange={(e) => setPath(e.target.value)}
disabled={traceStarted}
/>
</Box>
Expand All @@ -403,9 +372,7 @@ const Trace = () => {
type="number"
placeholder="e.g. website.io.3249.114.12"
value={`${threshold}`}
onChange={(e) => {
setThreshold(parseInt(e.target.value));
}}
onChange={(e) => setThreshold(parseInt(e.target.value))}
disabled={traceStarted}
/>
</Box>
Expand All @@ -423,9 +390,7 @@ const Trace = () => {
id={"only_errors"}
name={"only_errors"}
label={"Display only Errors"}
onChange={() => {
setErrors(!errors);
}}
onChange={() => setErrors(!errors)}
value={"only_errors"}
disabled={traceStarted}
/>
Expand Down
36 changes: 8 additions & 28 deletions web-app/yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -10429,6 +10429,11 @@ react-transition-group@^4.4.5:
loose-envify "^1.4.0"
prop-types "^15.6.2"

react-use-websocket@^4.8.1:
version "4.8.1"
resolved "https://registry.yarnpkg.com/react-use-websocket/-/react-use-websocket-4.8.1.tgz#be06a0bc956c6d56391a29cbe2caa6ae8edb5615"
integrity sha512-FTXuG5O+LFozmu1BRfrzl7UIQngECvGJmL7BHsK4TYXuVt+mCizVA8lT0hGSIF0Z0TedF7bOo1nRzOUdginhDw==

react-virtual@^2.8.2:
version "2.10.4"
resolved "https://registry.yarnpkg.com/react-virtual/-/react-virtual-2.10.4.tgz#08712f0acd79d7d6f7c4726f05651a13b24d8704"
Expand Down Expand Up @@ -11399,16 +11404,7 @@ string-natural-compare@^3.0.1:
resolved "https://registry.yarnpkg.com/string-natural-compare/-/string-natural-compare-3.0.1.tgz#7a42d58474454963759e8e8b7ae63d71c1e7fdf4"
integrity sha512-n3sPwynL1nwKi3WJ6AIsClwBMa0zTi54fn2oLU6ndfTSIO05xaznjSf15PcBZU6FNWbmN5Q6cxT4V5hGvB4taw==

"string-width-cjs@npm:string-width@^4.2.0":
version "4.2.3"
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
dependencies:
emoji-regex "^8.0.0"
is-fullwidth-code-point "^3.0.0"
strip-ansi "^6.0.1"

"string-width@^1.0.2 || 2 || 3 || 4", string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3:
"string-width-cjs@npm:string-width@^4.2.0", "string-width@^1.0.2 || 2 || 3 || 4", string-width@^4.1.0, string-width@^4.2.0, string-width@^4.2.3:
version "4.2.3"
resolved "https://registry.yarnpkg.com/string-width/-/string-width-4.2.3.tgz#269c7117d27b05ad2e536830a8ec895ef9c6d010"
integrity sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==
Expand Down Expand Up @@ -11503,14 +11499,7 @@ stringify-object@^3.3.0:
is-obj "^1.0.1"
is-regexp "^1.0.0"

"strip-ansi-cjs@npm:strip-ansi@^6.0.1":
version "6.0.1"
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
dependencies:
ansi-regex "^5.0.1"

strip-ansi@^6.0.0, strip-ansi@^6.0.1:
"strip-ansi-cjs@npm:strip-ansi@^6.0.1", strip-ansi@^6.0.0, strip-ansi@^6.0.1:
version "6.0.1"
resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-6.0.1.tgz#9e26c63d30f53443e9489495b2105d37b67a85d9"
integrity sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==
Expand Down Expand Up @@ -13260,7 +13249,7 @@ workbox-window@6.6.1:
"@types/trusted-types" "^2.0.2"
workbox-core "6.6.1"

"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0":
"wrap-ansi-cjs@npm:wrap-ansi@^7.0.0", wrap-ansi@^7.0.0:
version "7.0.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==
Expand All @@ -13278,15 +13267,6 @@ wrap-ansi@^6.2.0:
string-width "^4.1.0"
strip-ansi "^6.0.0"

wrap-ansi@^7.0.0:
version "7.0.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-7.0.0.tgz#67e145cff510a6a6984bdf1152911d69d2eb9e43"
integrity sha512-YVGIj2kamLSTxw6NsZjoBxfSwsn0ycdesmc4p+Q21c5zPuZ1pl+NfxVdxPtdHvmNVOQ6XSYG4AUtyt/Fi7D16Q==
dependencies:
ansi-styles "^4.0.0"
string-width "^4.1.0"
strip-ansi "^6.0.0"

wrap-ansi@^8.1.0:
version "8.1.0"
resolved "https://registry.yarnpkg.com/wrap-ansi/-/wrap-ansi-8.1.0.tgz#56dc22368ee570face1b49819975d9b9a5ead214"
Expand Down

0 comments on commit 2f96f07

Please sign in to comment.