diff --git a/src/components/TopologyCard/Property.tsx b/src/components/TopologyCard/Property.tsx
index 3f38d5b243..8e7c3e5162 100644
--- a/src/components/TopologyCard/Property.tsx
+++ b/src/components/TopologyCard/Property.tsx
@@ -5,6 +5,7 @@ import { Age } from "../../ui/Age";
import { isEmpty } from "../Canary/utils";
import { Icon } from "../Icon";
import {
+ FormatPropertyCPUMemory,
FormatPropertyCurrency,
FormatPropertyDefault,
FormatPropertyURL
@@ -36,6 +37,10 @@ export function FormatProperty({
return ;
}
+ if (property.name === "cpu" || property.name === "memory") {
+ return ;
+ }
+
return ;
}
diff --git a/src/components/TopologyCard/Utils/FormatProperties.tsx b/src/components/TopologyCard/Utils/FormatProperties.tsx
index b97d405281..83ba6e0869 100644
--- a/src/components/TopologyCard/Utils/FormatProperties.tsx
+++ b/src/components/TopologyCard/Utils/FormatProperties.tsx
@@ -3,6 +3,7 @@ import React, { useMemo, useState } from "react";
import { formatBytes } from "../../../utils/common";
import { isEmpty } from "lodash";
import { TopologyProperty } from "../../../api/types/topology";
+import ProgressBar from "../../../ui/stats/ProgressBar";
type FormatPropertyProps = {
property?: TopologyProperty;
@@ -74,6 +75,38 @@ function convertUnitsToDisplayValue(value: number, unit?: string) {
return value;
}
+export function FormatPropertyCPUMemory({ property }: FormatPropertyProps) {
+ if (
+ !property ||
+ !property.value ||
+ (property?.name !== "cpu" && property?.name !== "memory")
+ ) {
+ return null;
+ }
+
+ const value = property.value;
+ const max = property.max;
+
+ const formattedMax =
+ property.name === "cpu"
+ ? (Number(max) / 1000).toFixed(2)
+ : formatBytes(Number(max), 1);
+
+ if (max) {
+ const percent = (Number(value) / Number(max)) * 100;
+ return (
+
+ );
+ }
+
+ return {value.toString()};
+}
+
export function FormatPropertyDefault({
property,
short
diff --git a/src/ui/stats/ProgressBar.stories.tsx b/src/ui/stats/ProgressBar.stories.tsx
new file mode 100644
index 0000000000..bbaacfa816
--- /dev/null
+++ b/src/ui/stats/ProgressBar.stories.tsx
@@ -0,0 +1,29 @@
+import React, { ComponentProps } from "react";
+import { Story, Meta } from "@storybook/react";
+import ProgressBar from "./ProgressBar";
+
+export default {
+ title: "ProgressBar",
+ component: ProgressBar
+} as Meta;
+
+const Template: Story> = (args) => (
+
+);
+
+export const FivePercent = Template.bind({});
+FivePercent.args = {
+ value: 5
+};
+
+export const FiftyPercent = Template.bind({});
+FiftyPercent.args = {
+ value: 50
+};
+
+export const EightyPercent = Template.bind({});
+EightyPercent.args = {
+ value: 80
+};
diff --git a/src/ui/stats/ProgressBar.tsx b/src/ui/stats/ProgressBar.tsx
new file mode 100644
index 0000000000..23e35b4e54
--- /dev/null
+++ b/src/ui/stats/ProgressBar.tsx
@@ -0,0 +1,29 @@
+import React, { CSSProperties } from "react";
+
+interface Props {
+ value: number;
+ className?: string;
+}
+
+export default function ProgressBar({ value, className = "h-3" }: Props) {
+ const barStyle: CSSProperties = {
+ width: `${value}%`,
+ backgroundColor: value > 70 ? "red" : "green"
+ };
+
+ const roundingClassName =
+ value < 25
+ ? "rounded-l-2xl"
+ : value > 50
+ ? "rounded-full"
+ : "rounded-l-xl rounded-r-xl";
+
+ return (
+
+ );
+}